You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
308 lines
5.9 KiB
308 lines
5.9 KiB
/* ============================================================
|
|
*
|
|
* This file is a part of digiKam project
|
|
* http://www.digikam.org
|
|
*
|
|
* Date : 2005-04-24
|
|
* Description : icons group item.
|
|
*
|
|
* Copyright (C) 2005 by Renchi Raju <renchi@pooh.tam.uiuc.edu>
|
|
*
|
|
* This program is free software; you can redistribute it
|
|
* and/or modify it under the terms of the GNU General
|
|
* Public License as published by the Free Software Foundation;
|
|
* either version 2, or (at your option)
|
|
* any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* ============================================================ */
|
|
|
|
// C Ansi includes.
|
|
|
|
#include <cstdlib>
|
|
|
|
// TQt includes.
|
|
|
|
#include <tqpixmap.h>
|
|
#include <tqpalette.h>
|
|
|
|
// Local includes.
|
|
|
|
#include "iconview.h"
|
|
#include "iconitem.h"
|
|
#include "icongroupitem.h"
|
|
|
|
namespace Digikam
|
|
{
|
|
|
|
class IconGroupItemPriv
|
|
{
|
|
public:
|
|
|
|
IconGroupItemPriv()
|
|
{
|
|
view = 0;
|
|
firstItem = 0;
|
|
lastItem = 0;
|
|
y = 0;
|
|
count = 0;
|
|
clearing = false;
|
|
}
|
|
|
|
IconView* view;
|
|
|
|
IconItem* firstItem;
|
|
IconItem* lastItem;
|
|
|
|
int y;
|
|
int count;
|
|
bool clearing;
|
|
|
|
struct SortableItem
|
|
{
|
|
IconItem *item;
|
|
};
|
|
};
|
|
|
|
IconGroupItem::IconGroupItem(IconView* parent)
|
|
{
|
|
d = new IconGroupItemPriv;
|
|
d->view = parent;
|
|
m_next = 0;
|
|
m_prev = 0;
|
|
|
|
parent->insertGroup(this);
|
|
}
|
|
|
|
IconGroupItem::~IconGroupItem()
|
|
{
|
|
clear(false);
|
|
d->view->takeGroup(this);
|
|
delete d;
|
|
}
|
|
|
|
IconView* IconGroupItem::iconView() const
|
|
{
|
|
return d->view;
|
|
}
|
|
|
|
IconGroupItem* IconGroupItem::nextGroup() const
|
|
{
|
|
return m_next;
|
|
}
|
|
|
|
IconGroupItem* IconGroupItem::prevGroup() const
|
|
{
|
|
return m_prev;
|
|
}
|
|
|
|
TQRect IconGroupItem::rect() const
|
|
{
|
|
TQRect r = d->view->bannerRect();
|
|
r.moveBy(0, d->y);
|
|
return r;
|
|
}
|
|
|
|
int IconGroupItem::y() const
|
|
{
|
|
return d->y;
|
|
}
|
|
|
|
IconItem* IconGroupItem::firstItem() const
|
|
{
|
|
return d->firstItem;
|
|
}
|
|
|
|
IconItem* IconGroupItem::lastItem() const
|
|
{
|
|
return d->lastItem;
|
|
}
|
|
|
|
void IconGroupItem::insertItem(IconItem* item)
|
|
{
|
|
if (!item)
|
|
return;
|
|
|
|
if (!d->firstItem)
|
|
{
|
|
d->firstItem = item;
|
|
d->lastItem = item;
|
|
item->m_prev = 0;
|
|
item->m_next = 0;
|
|
}
|
|
else
|
|
{
|
|
d->lastItem->m_next = item;
|
|
item->m_prev = d->lastItem;
|
|
item->m_next = 0;
|
|
d->lastItem = item;
|
|
}
|
|
|
|
d->count++;
|
|
d->view->insertItem(item);
|
|
}
|
|
|
|
void IconGroupItem::takeItem(IconItem* item)
|
|
{
|
|
if (!item)
|
|
return;
|
|
|
|
// take item triggers update
|
|
d->view->takeItem(item);
|
|
d->count--;
|
|
|
|
if (item == d->firstItem)
|
|
{
|
|
d->firstItem = d->firstItem->m_next;
|
|
if (d->firstItem)
|
|
d->firstItem->m_prev = 0;
|
|
else
|
|
d->firstItem = d->lastItem = 0;
|
|
}
|
|
else if (item == d->lastItem)
|
|
{
|
|
d->lastItem = d->lastItem->m_prev;
|
|
if ( d->lastItem )
|
|
d->lastItem->m_next = 0;
|
|
else
|
|
d->firstItem = d->lastItem = 0;
|
|
}
|
|
else
|
|
{
|
|
IconItem *i = item;
|
|
if (i)
|
|
{
|
|
if (i->m_prev )
|
|
i->m_prev->m_next = i->m_next;
|
|
if ( i->m_next )
|
|
i->m_next->m_prev = i->m_prev;
|
|
}
|
|
}
|
|
}
|
|
|
|
int IconGroupItem::count() const
|
|
{
|
|
return d->count;
|
|
}
|
|
|
|
int IconGroupItem::index(IconItem* item) const
|
|
{
|
|
if ( !item )
|
|
return -1;
|
|
|
|
if ( item == d->firstItem )
|
|
return 0;
|
|
else if ( item == d->lastItem )
|
|
return d->count - 1;
|
|
else
|
|
{
|
|
IconItem *i = d->firstItem;
|
|
int j = 0;
|
|
while ( i && i != item )
|
|
{
|
|
i = i->m_next;
|
|
++j;
|
|
}
|
|
|
|
return i ? j : -1;
|
|
}
|
|
}
|
|
|
|
void IconGroupItem::clear(bool update)
|
|
{
|
|
d->clearing = true;
|
|
|
|
IconItem *item = d->firstItem;
|
|
while (item)
|
|
{
|
|
IconItem *tmp = item->m_next;
|
|
delete item;
|
|
item = tmp;
|
|
}
|
|
|
|
d->firstItem = 0;
|
|
d->lastItem = 0;
|
|
d->count = 0;
|
|
|
|
if (update)
|
|
d->view->triggerRearrangement();
|
|
|
|
d->clearing = false;
|
|
}
|
|
|
|
void IconGroupItem::sort()
|
|
{
|
|
IconGroupItemPriv::SortableItem *items
|
|
= new IconGroupItemPriv::SortableItem[ count() ];
|
|
|
|
IconItem *item = d->firstItem;
|
|
int i = 0;
|
|
for ( ; item; item = item->m_next )
|
|
items[ i++ ].item = item;
|
|
|
|
qsort( items, count(), sizeof( IconGroupItemPriv::SortableItem ), cmpItems );
|
|
|
|
IconItem *prev = 0;
|
|
item = 0;
|
|
for ( i = 0; i < (int)count(); ++i ) {
|
|
item = items[ i ].item;
|
|
if ( item ) {
|
|
item->m_prev = prev;
|
|
if ( item->m_prev )
|
|
item->m_prev->m_next = item;
|
|
item->m_next = 0;
|
|
}
|
|
if ( i == 0 )
|
|
d->firstItem = item;
|
|
if ( i == (int)count() - 1 )
|
|
d->lastItem = item;
|
|
prev = item;
|
|
}
|
|
|
|
delete [] items;
|
|
}
|
|
|
|
bool IconGroupItem::move(int y)
|
|
{
|
|
if (d->y == y)
|
|
return false;
|
|
|
|
d->y = y;
|
|
return true;
|
|
}
|
|
|
|
void IconGroupItem::paintBanner()
|
|
{
|
|
TQRect r(rect());
|
|
TQPixmap pix(r.width(), r.height());
|
|
pix.fill(d->view->colorGroup().base());
|
|
|
|
r = TQRect(d->view->contentsToViewport(TQPoint(r.x(), r.y())),
|
|
TQSize(r.width(), r.height()));
|
|
|
|
bitBlt(d->view->viewport(), r.x(), r.y(), &pix,
|
|
0, 0, r.width(), r.height());
|
|
}
|
|
|
|
int IconGroupItem::compare(IconGroupItem*)
|
|
{
|
|
return 0;
|
|
}
|
|
|
|
int IconGroupItem::cmpItems(const void *n1, const void *n2)
|
|
{
|
|
if ( !n1 || !n2 )
|
|
return 0;
|
|
|
|
IconGroupItemPriv::SortableItem *i1 = (IconGroupItemPriv::SortableItem *)n1;
|
|
IconGroupItemPriv::SortableItem *i2 = (IconGroupItemPriv::SortableItem *)n2;
|
|
|
|
return i1->item->compare( i2->item );
|
|
}
|
|
|
|
} // namespace Digikam
|