OSDN Git Service

ImageListViewItem.GetImageAsync() の実行にawaitを使用するよう修正
authorKimura Youichi <kim.upsilon@bucyou.net>
Sun, 13 Apr 2014 09:37:10 +0000 (18:37 +0900)
committerKimura Youichi <kim.upsilon@bucyou.net>
Sun, 13 Apr 2014 12:34:08 +0000 (21:34 +0900)
OpenTween/ImageListViewItem.cs
OpenTween/Tween.cs

index 1bf9241..90c0071 100644 (file)
@@ -38,6 +38,7 @@ namespace OpenTween
         protected readonly string imageUrl;
 
         private WeakReference imageReference = new WeakReference(null);
+        private Task imageTask = null;
 
         public event EventHandler ImageDownloaded;
 
@@ -56,18 +57,29 @@ namespace OpenTween
             {
                 var image = imageCache.TryGetFromCache(imageUrl);
 
-                if (image == null)
-                    this.GetImageAsync();
-                else
+                if (image != null)
                     this.imageReference.Target = image;
             }
         }
 
-        private async Task GetImageAsync(bool force = false)
+        public Task GetImageAsync(bool force = false)
+        {
+            if (this.imageTask == null || this.imageTask.IsCompleted)
+            {
+                this.imageTask = this.GetImageAsyncInternal(force);
+            }
+
+            return this.imageTask;
+        }
+
+        private async Task GetImageAsyncInternal(bool force)
         {
             if (string.IsNullOrEmpty(this.imageUrl))
                 return;
 
+            if (!force && this.imageReference.Target != null)
+                return;
+
             try
             {
                 var image = await this.imageCache.DownloadImageAsync(this.imageUrl, force);
index 7391ac5..5c573eb 100644 (file)
@@ -5166,34 +5166,33 @@ namespace OpenTween
             finally { this.itemCacheLock.ExitUpgradeableReadLock(); }
         }
 
-        private void MyList_RetrieveVirtualItem(object sender, RetrieveVirtualItemEventArgs e)
+        private async void MyList_RetrieveVirtualItem(object sender, RetrieveVirtualItemEventArgs e)
         {
-            ListViewItem cacheItem = null;
+            ListViewItem item = null;
             PostClass cacheItemPost = null;
 
-            this.TryGetListViewItemCache(e.ItemIndex, out cacheItem, out cacheItemPost);
+            this.TryGetListViewItemCache(e.ItemIndex, out item, out cacheItemPost);
 
-            if (cacheItem != null)
-            {
-                e.Item = cacheItem;
-            }
-            else
+            if (item == null)
             {
                 //A cache miss, so create a new ListViewItem and pass it back.
                 TabPage tb = (TabPage)((DetailsListView)sender).Parent;
                 try
                 {
-                    e.Item = CreateItem(tb,
-                                        _statuses[tb.Text, e.ItemIndex],
-                                        e.ItemIndex);
+                    item = this.CreateItem(tb, _statuses[tb.Text, e.ItemIndex], e.ItemIndex);
                 }
                 catch (Exception)
                 {
                     //不正な要求に対する間に合わせの応答
                     string[] sitem = {"", "", "", "", "", "", "", ""};
-                    e.Item = new ImageListViewItem(sitem);
+                    item = new ImageListViewItem(sitem);
                 }
             }
+
+            // e.Item に値をセットする前に await しないこと
+            e.Item = item;
+
+            await ((ImageListViewItem)item).GetImageAsync();
         }
 
         private void CreateCache(int StartIndex, int EndIndex)