[prev in list] [next in list] [prev in thread] [next in thread]
List: kfm-devel
Subject: Re: Icons Layout and Previews
From: Benoit Walter <b.walter () free ! fr>
Date: 2003-11-03 22:11:57
[Download RAW message or body]
I have improved this patch and this should work better now. The iconview is
now updated only for visible icons, otherwise the update is delayed.
It fixes a bug and does not change any i18n string. Can someone review it?
Benoit.
On Monday 03 November 2003 00:01, Benoit Walter wrote:
> Hi,
>
> I have tried to improve the painting of thumbnails during preview
> generation. The problem of overlapped icons has been partially adressed by
> updating the iconview every 500ms (kfileivi.cc revision 1.250). This does
> not really solve the problem because the display remains ugly while
> generating preview during 500ms.
> With the following patch, the icon view is updated when a new thumbnail has
> been generated, but only if the update is needed (in most cases once for
> each row). Otherwise, the icon is moved. This avoids having a messy icon
> layout during generation of thumbnails.
>
> Possible improvement:
> Update the view less frequently when the generated thumbnail is not
> visible.
>
> This solution is not yet perfect and it would be great if someone could try
> the patch and give some comments.
>
> Cheers,
> Benoit.
["libkonq_preview.diff" (text/x-diff)]
Index: konq_iconviewwidget.cc
===================================================================
RCS file: /home/kde/kdebase/libkonq/konq_iconviewwidget.cc,v
retrieving revision 1.266
diff -u -3 -p -r1.266 konq_iconviewwidget.cc
--- konq_iconviewwidget.cc 24 Oct 2003 20:46:48 -0000 1.266
+++ konq_iconviewwidget.cc 3 Nov 2003 22:04:14 -0000
@@ -337,7 +337,7 @@ struct KonqIconViewWidgetPrivate
pSoundTimer = 0;
pPreviewJob = 0;
bAllowSetWallpaper = false;
- gridXspacing = 50;
+ gridXspacing = 50;
doAnimations = true;
m_movie = 0L;
@@ -362,7 +362,6 @@ struct KonqIconViewWidgetPrivate
bool bSoundItemClicked;
bool bAllowSetWallpaper;
int gridXspacing;
-
QTimer* rearrangeIconsTimer;
// Animated icons support
@@ -680,26 +679,62 @@ void KonqIconViewWidget::slotStartSoundP
void KonqIconViewWidget::slotPreview(const KFileItem *item, const QPixmap &pix)
{
+ int left = contentsX();
+ int right = left + viewport()->width();
+ int top = contentsY();
+ int bottom = top + viewport()->height();
+
// ### slow. Idea: move KonqKfmIconView's m_itemDict into this class
for (QIconViewItem *it = firstItem(); it; it = it->nextItem())
{
KFileIVI* current = static_cast<KFileIVI *>(it);
if (current->item() == item)
{
- bool needsUpdate = ( !current->pixmap() || current->pixmap()->width() < \
pix.width() || current->pixmap()->height() < pix.height() );
- if(item->overlays() & KIcon::HiddenOverlay)
- {
- QPixmap p(pix);
+ bool itemIsVisible =
+ ( current->x() > left ) &&
+ ( current->x() < right ) &&
+ ( current->y() > top ) &&
+ ( current->y() < bottom );
+ bool rearranged = false;
+ if (item->overlays() & KIcon::HiddenOverlay) {
+ QPixmap p(pix);
KIconEffect::semiTransparent(p);
+ if ( autoArrange() )
+ rearranged = rearrangeIcon(current, p);
current->setThumbnailPixmap(p);
- } else {
+ }
+ else {
+ if (autoArrange())
+ rearranged = rearrangeIcon(current, pix);
current->setThumbnailPixmap(pix);
}
- if ( needsUpdate
- && autoArrange()
- && !d->rearrangeIconsTimer->isActive() ) {
- d->rearrangeIconsTimer->start( 500, true );
+
+ if (!autoArrange())
+ continue;
+
+ // Force immediate if the icon is too far on the right
+ bool forceUpdate =
+ ( itemTextPos() == QIconView::Bottom &&
+ contentsWidth() > viewport()->width() &&
+ viewport()->width() > 200 ) ||
+ ( itemTextPos() == QIconView::Right &&
+ contentsHeight() > viewport()->height() &&
+ viewport()->height() > 170 );
+
+ // If the item is visible and has not been rearranged, we
+ // update the view immediately
+ if ( ((itemIsVisible && !rearranged) || forceUpdate) &&
+ !d->rearrangeIconsTimer->isActive() )
+ d->rearrangeIconsTimer->start( 20, true );
+
+ // If the item is not visible and has not been rearranged, we
+ // will update the view later (after all previews have been
+ // generated or after scrolling)
+ else if (!itemIsVisible && !rearranged &&
+ !d->rearrangeIconsTimer->isActive() ) {
+ connect( this, SIGNAL( contentsMoving(int,int) ),
+ this, SLOT( slotRearrangeIcons(int,int) ) );
}
}
}
@@ -708,10 +743,6 @@ void KonqIconViewWidget::slotPreview(con
void KonqIconViewWidget::slotPreviewResult()
{
d->pPreviewJob = 0;
- if ( d->rearrangeIconsTimer->isActive() ) {
- d->rearrangeIconsTimer->stop();
- slotRearrangeIcons();
- }
emit imagePreviewFinished();
}
@@ -1083,10 +1114,16 @@ void KonqIconViewWidget::slotAboutToCrea
void KonqIconViewWidget::slotRearrangeIcons()
{
- // We cannot actually call arrangeItemsInGrid directly as a slot because it has \
a default parameter.
- arrangeItemsInGrid();
+ // We cannot actually call arrangeItemsInGrid directly as a slot because it has a \
default parameter. + arrangeItemsInGrid();
}
+void KonqIconViewWidget::slotRearrangeIcons( int, int )
+{
+ disconnect( this, SIGNAL( contentsMoving(int,int) ),
+ this, SLOT( slotRearrangeIcons(int,int) ) );
+ arrangeItemsInGrid();
+}
void KonqIconViewWidget::drawBackground( QPainter *p, const QRect &r )
{
@@ -1977,6 +2014,62 @@ void KonqIconViewWidget::setNewURL( cons
else
u = url;
setURL( u );
+}
+
+bool KonqIconViewWidget::rearrangeIcon( KFileIVI* item, const QPixmap& pixmap )
+{
+ int maxHeight = 0;
+ int maxTop = 0;
+
+ // Text at bottom of icons
+ if ( itemTextPos() == QIconView::Bottom ) {
+
+ // Look for item of max height on the left of item
+ KFileIVI* thumb = static_cast<KFileIVI*> ( item->prevItem() );
+ while ( thumb && thumb->x() < item->x() ) {
+ int currentHeight = thumb->pixmap()->height();
+ if ( currentHeight > maxHeight ) {
+ maxHeight = currentHeight;
+ maxTop = thumb->rect().top();
+ }
+ thumb = static_cast<KFileIVI*> ( thumb->prevItem() );
+ }
+
+ // Look for item of max height on the right of item
+ thumb = static_cast<KFileIVI*> ( item->nextItem() );
+ while ( thumb && thumb->x() > item->x() ) {
+ int currentHeight = thumb->pixmap()->height();
+ if ( currentHeight > maxHeight ) {
+ maxHeight = currentHeight;
+ maxTop = thumb->rect().top();
+ }
+ thumb = static_cast<KFileIVI*> ( thumb->nextItem() );
+ }
+ }
+
+ // Text alongside icons
+ else {
+ // Height of the current icon (not yet thumbnail)
+ maxHeight = item->pixmap()->height();
+ maxTop = item->rect().top();
+ }
+
+ // If maxHeight > currentHeight, move and resize current icon
+ int currentHeight = pixmap.height();
+ if ( maxHeight >= currentHeight ) {
+ QRect tmpRect = item->rect();
+ // Center icon horizontally if needed
+ if ( itemTextPos() == QIconView::Bottom &&
+ item->textRect().width() < pixmap.width() ) {
+ tmpRect.setLeft(
+ tmpRect.left() - ( pixmap.width() - tmpRect.width() ) / 2 );
+ }
+ // Top of icon
+ tmpRect.setTop( maxTop + maxHeight - currentHeight );
+ item->changeLayout( tmpRect ); // cannot use setItemLayout directly
+ return true; // Icon has been rearranged
+ }
+ return false; // Icon could not be rearranged, we need to update the view
}
#include "konq_iconviewwidget.moc"
[prev in list] [next in list] [prev in thread] [next in thread]
Configure |
About |
News |
Add a list |
Sponsored by KoreLogic