From 0626d901b95f3f81ce2c6de679537add5c8d64b1 Mon Sep 17 00:00:00 2001 From: Kirill Kalishev Date: Sun, 7 Mar 2010 13:25:23 +0300 Subject: [PATCH] IDEA-52627 - Icons for native files in project view flicker --- .../impl/NativeFileIconProvider.java | 29 ++++++++++++++++--- .../src/com/intellij/util/IconUtil.java | 11 +++++-- 2 files changed, 34 insertions(+), 6 deletions(-) diff --git a/platform/lang-impl/src/com/intellij/openapi/fileTypes/impl/NativeFileIconProvider.java b/platform/lang-impl/src/com/intellij/openapi/fileTypes/impl/NativeFileIconProvider.java index 4212135e063f..a55591b588d5 100644 --- a/platform/lang-impl/src/com/intellij/openapi/fileTypes/impl/NativeFileIconProvider.java +++ b/platform/lang-impl/src/com/intellij/openapi/fileTypes/impl/NativeFileIconProvider.java @@ -24,6 +24,7 @@ import com.intellij.openapi.util.SystemInfo; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.ui.DeferredIconImpl; import com.intellij.util.Function; +import com.intellij.util.ui.update.ComparableObject; import org.jetbrains.annotations.Nullable; import javax.swing.*; @@ -35,17 +36,19 @@ import java.util.*; */ public class NativeFileIconProvider implements FileIconProvider { private JFileChooser myFileChooser = new JFileChooser(); - private final Map myIconCache = new HashMap(); + private final Map myIconCache = new HashMap(); // on Windows .exe and .ico files provide their own icons which can differ for each file, cache them by full file path - private final Set myCustomIconExtensions = - SystemInfo.isWindows ? new HashSet(Arrays.asList("exe", "ico")) : new HashSet(); + private final Set myCustomIconExtensions = + SystemInfo.isWindows ? new HashSet(Arrays.asList(new Ext("exe"), new Ext("ico"))) : new HashSet(); private final Map myCustomIconCache = new HashMap(); + private static final Ext NO_EXT = new Ext(null); + public Icon getIcon(VirtualFile file, int flags, @Nullable Project project) { if (!(file.getFileType() instanceof NativeFileType) && !(file.getFileType() instanceof UnknownFileType)) { return null; } - final String ext = file.getExtension(); + final Ext ext = file.getExtension() != null ? new Ext(file.getExtension()) : NO_EXT; final String filePath = file.getPath(); Icon icon; @@ -87,4 +90,22 @@ public class NativeFileIconProvider implements FileIconProvider { } }); } + + private static class Ext extends ComparableObject.Impl { + + private final Object[] myText; + + private Ext(@Nullable String text) { + myText = new Object[] {text}; + } + + public Object[] getEqualityObjects() { + return myText; + } + + @Override + public String toString() { + return myText[0] != null ? myText[0].toString() : null; + } + } } diff --git a/platform/platform-api/src/com/intellij/util/IconUtil.java b/platform/platform-api/src/com/intellij/util/IconUtil.java index ae0e5233ba62..cbd8efe22e2b 100644 --- a/platform/platform-api/src/com/intellij/util/IconUtil.java +++ b/platform/platform-api/src/com/intellij/util/IconUtil.java @@ -23,6 +23,7 @@ import com.intellij.openapi.project.DumbService; import com.intellij.openapi.project.Project; import com.intellij.openapi.util.IconLoader; import com.intellij.openapi.util.Iconable; +import com.intellij.openapi.util.Key; import com.intellij.openapi.vfs.VirtualFile; import com.intellij.ui.IconDeferrer; import com.intellij.ui.RowIcon; @@ -35,6 +36,8 @@ import javax.swing.*; public class IconUtil { + public static final Key LAST_FILE_ICON = Key.create("lastVFileIcon"); + private IconUtil() { } @@ -85,7 +88,9 @@ public class IconUtil { } public static Icon getIcon(final VirtualFile file, final int flags, final Project project) { - return IconDeferrer.getInstance().defer(file.getIcon(), new FileIconKey(file, project, flags), new Function() { + Icon lastIcon = file.getUserData(LAST_FILE_ICON); + + return IconDeferrer.getInstance().defer(lastIcon != null ? lastIcon : file.getIcon(), new FileIconKey(file, project, flags), new Function() { public Icon fun(final FileIconKey key) { VirtualFile file = key.getFile(); int flags = key.getFlags(); @@ -106,9 +111,11 @@ public class IconUtil { } if ((flags & Iconable.ICON_FLAG_READ_STATUS) != 0 && !file.isWritable()) { - return new LayeredIcon(icon, Icons.LOCKED_ICON); + icon = new LayeredIcon(icon, Icons.LOCKED_ICON); } + file.putUserData(LAST_FILE_ICON, icon); + return icon; } });