프로젝트

일반

사용자정보

통계
| 브랜치(Branch): | 개정판:

markus / KCOM / PageManager / PageStorage - 복사본.cs @ 9d5b4bc2

이력 | 보기 | 이력해설 | 다운로드 (11.3 KB)

1
using System;
2
using System.Collections.Concurrent;
3
using System.Collections.Generic;
4
using System.ComponentModel;
5
using System.Linq;
6
using System.Text;
7
using System.Threading.Tasks;
8
using System.Windows.Media.Imaging;
9

    
10
namespace KCOM.PageManager
11
{
12
    public class PageStorage
13
    {
14
        private const int DEFUALT_TALK_PAGE_COUNT = 10;
15

    
16
        public event EventHandler<PageLoadCompletedEventArgs> PageLoadCompleted;
17

    
18
        List<int> WorkItems = new List<int>();
19
        ConcurrentBag<PageItem> fileItems = new ConcurrentBag<PageItem>();
20
        BackgroundWorker backgroundWorker;
21

    
22
        //List<PageItem> fileItems = new List<PageItem>();
23
        string _localStorage;
24
        string _fileExt;
25
        string _BaseUri;
26
        int _TotalPages;
27
        int _TakeCount;
28

    
29
        bool IsDownload = false;
30

    
31
        BitmapFrame PageImage;
32

    
33
        public PageStorage(string BaseUri, string localStoragePath,string fileExt,int totalPages,int takeCount = 5)
34
        {
35
            try
36
            {
37
                backgroundWorker = new BackgroundWorker {WorkerSupportsCancellation = true,WorkerReportsProgress = true};
38
                backgroundWorker.DoWork += BackgroundWorker_DoWork;
39
                backgroundWorker.ProgressChanged += BackgroundWorker_ProgressChanged;
40
                _fileExt = fileExt;
41
                _BaseUri = BaseUri;
42
                _localStorage = localStoragePath;
43
                _TotalPages = totalPages;
44
                _TakeCount = takeCount;
45

    
46
                System.IO.Directory.CreateDirectory(_localStorage);
47

    
48
                //backgroundWorker.RunWorkerAsync(new int[] { 1, 10 });
49
            }
50
            catch (Exception ex)
51
            {
52
                throw new Exception("PageStorage", ex);
53
            }
54
        }
55

    
56
        private void BackgroundWorker_ProgressChanged(object sender, ProgressChangedEventArgs e)
57
        {
58
            System.Diagnostics.Debug.WriteLine(_fileExt + ":" + e.ProgressPercentage.ToString() + "%");
59
        }
60

    
61
        private async void BackgroundWorker_DoWork(object sender, DoWorkEventArgs e)
62
        {
63
     
64
                while (WorkItems.Count > 0)
65
                {
66
                    if (!IsDownload)
67
                    {
68
                        int item = -1;
69
                        try
70
                        {
71

    
72
                            if (WorkItems.TryFrist(true,out item))
73
                            {
74
                                var result = await DownloadPageAsync(item, null);
75

    
76
                                if(!result.IsDownLoad)
77
                                {
78
                                    System.Threading.Thread.Sleep(100);
79
                                }
80
                            await Task.Delay(100);
81
                            //System.Threading.Thread.Sleep(10);
82
                            //backgroundWorker.ReportProgress(fileItems.Count / _TotalPages * 100);
83
                        }
84
                        }
85
                        catch (Exception ex)
86
                        {
87
                            System.Diagnostics.Debug.WriteLine(ex.ToString());
88
                        }
89
                    }
90
              }
91
      }
92

    
93
        public void ResetImage()
94
        {
95
            //if (PageImage != null)
96
            //{
97
            //    PageImage = null;
98
            //}
99

    
100
            //PageImage.CreateOptions = BitmapCreateOptions.IgnoreImageCache;
101

    
102
        }
103

    
104
        public async Task<BitmapFrame> GetPageImageAsync(System.Threading.CancellationToken cts,int PageNo,bool IsRestart =false)
105
        {
106
            try
107
            {
108

    
109
                var localUri = await GetPageUriAsync(null,PageNo);
110

    
111
                if (localUri != null || !cts.IsCancellationRequested)
112
                {
113
                    PageImage = BitmapFrame.Create(localUri, BitmapCreateOptions.None, BitmapCacheOption.OnLoad);
114
                }
115
            }
116
            catch (Exception ex)
117
            {
118
                throw new Exception("GetPageImageAsync(int PageNo,bool IsRestart =false)", ex);
119
            }
120
            finally
121
            {
122
            }
123

    
124
            return PageImage;
125
        }
126

    
127
        private void DownloadWorkAsync(int startPage,int TakeCount)
128
        {
129
           
130
            lock(WorkItems)
131
            {
132
                WorkItems.AddRange(Enumerable.Range(startPage, TakeCount));
133
            }
134

    
135
            if (TakeCount == _TotalPages)
136
            {
137
                _TakeCount = 0;
138
            }
139

    
140
           // var files = fileItems.Select(x => x.PageNo);
141

    
142

    
143
            //for (int i = startPage; i < TakeCount + 1; i++)
144
            //{
145
            //    if (i < _TotalPages && !WorkItems.Contains(i) && !files.Contains(i))
146
            //    {
147
            //        WorkItems.Add(i);
148
            //       // System.Threading.Thread.Sleep(1);
149
            //    }
150
            //    else if(i == _TotalPages)
151
            //    {
152
            //        _TakeCount = 0;
153
            //    }
154
            //}
155

    
156
            if (!backgroundWorker.IsBusy && WorkItems.Count() > 0)
157
            {
158
                backgroundWorker.RunWorkerAsync();
159
            }
160
            
161
            //await Task.Delay(10);//  System.Threading.Thread.Sleep(10);
162
            //while (WorkItems.Count > 0)
163
            //{
164
            //    int item = -1;
165

    
166
            //    if (WorkItems.TryDequeue(out item))
167
            //    {
168
            //        var result = await DownloadPageAsync(item, null);
169
            //    }
170

    
171
            //}
172

    
173
        }
174

    
175
        public async Task<Uri> GetPageUriAsync( System.Threading.CancellationToken? cts, int PageNo, bool IsRestart = false)
176
        {
177
            Uri result = null;
178

    
179
            try
180
            {
181
                System.Diagnostics.Debug.WriteLine("GetPageAsync");
182

    
183
                var pageItem = await DownloadPageAsync(PageNo,cts);
184
                
185
                if (pageItem != null && 0 < _TakeCount && PageNo + 1 < _TotalPages)
186
                {
187
                    int takecount = _TakeCount;
188

    
189
                    if (_TotalPages < PageNo + 1 + takecount)
190
                    {
191
                        takecount = takecount - (PageNo + 1 + takecount - _TotalPages) -1;
192
                    }
193

    
194
                    DownloadWorkAsync(PageNo + 1, takecount);
195
                    //var takePageNoList = Enumerable.Range(PageNo + 1, _TakeCount);
196

    
197

    
198
                }
199

    
200
                result = pageItem.LocalUri;
201
            }
202
            catch (Exception ex)
203
            {
204
                if (cts != null)
205
                {
206
                    if (cts.Value.IsCancellationRequested)
207
                    {
208
                        return result;
209
                    }
210
                }
211

    
212
                if (!IsRestart)
213
                {
214
                    await Task.Delay(100);
215

    
216
                    result = await GetPageUriAsync(cts,PageNo, true);
217
                }
218
                //throw new Exception("GetPageAsync(string BasePageUri,int PageNo)", ex);
219
            }
220
            finally
221
            {
222
            }
223

    
224
            return result;
225
        }
226

    
227
        public async Task<PageItem> DownloadPageAsync(int PageNo,System.Threading.CancellationToken? cts)
228
        {
229
            PageItem result = new PageItem { PageNo = PageNo };
230

    
231
            try
232
            {
233
                var page = fileItems.Where(x => x.PageNo == PageNo).ToList();
234

    
235
                if (page.Count > 0)
236
                {
237
                    System.Diagnostics.Debug.WriteLine("DownloadPageAsync fileItems");
238

    
239
                    result = page.First();
240

    
241
                    /// 파일 체크 후 없으면 다시 다운로드
242
                    if (!System.IO.File.Exists(result.LocalFilePath))
243
                    {
244
                        //fileItems.(result);
245

    
246
                        result = await DownloadPageAsync(PageNo,cts);
247
                    }
248
                }
249
                else
250
                {
251

    
252
                    System.Diagnostics.Debug.WriteLine("DownloadPageAsync down");
253

    
254
                    string downloadFilePath = System.IO.Path.Combine(_localStorage, PageNo.ToString() + "." + _fileExt);
255

    
256
                    Uri originalUri = new Uri(_BaseUri.Replace("{PageNo}", PageNo.ToString()));
257

    
258
                    result = new PageItem
259
                    {
260
                        PageNo = PageNo,
261
                        OriginalUri = originalUri,
262
                        LocalUri = new Uri(downloadFilePath, UriKind.Absolute),
263
                        LocalFilePath = downloadFilePath
264
                    };
265

    
266
                    if(fileItems.Where(x => x.PageNo == PageNo).Count() == 0)
267
                    {
268
                        fileItems.Add(result);
269
                    }
270

    
271
                    using (System.Net.WebClient client = new System.Net.WebClient())
272
                    {
273
                        client.UseDefaultCredentials = true;
274
                        System.Net.IWebProxy webProxy = client.Proxy;
275

    
276
                        if (webProxy != null)
277
                        {
278
                            // Use the default credentials of the logged on user.
279
                            webProxy.Credentials = System.Net.CredentialCache.DefaultCredentials;
280
                        }
281

    
282
                        //client.DownloadFileCompleted += (snd, evt) =>
283
                        //{
284

    
285

    
286
                        //    //(snd as System.Net.WebClient).Dispose();
287
                        //};
288

    
289
                        if (cts != null)
290
                        {
291
                            client.DownloadProgressChanged += (snd, ect) =>
292
                            {
293
                                IsDownload = client.IsBusy;
294

    
295
                                if (cts.Value.IsCancellationRequested)
296
                                {
297
                                    client.CancelAsync();
298
                                }
299
                            };
300
                        }
301

    
302
                        client.DownloadFileCompleted += (snd, evt) =>
303
                        {
304
                            result.IsDownLoad = true;
305
                            System.Diagnostics.Debug.WriteLine("Download : " + downloadFilePath);
306

    
307
                            PageLoadCompleted?.Invoke(this, new PageLoadCompletedEventArgs(result));
308
                        };
309

    
310
                        await client.DownloadFileTaskAsync(originalUri, downloadFilePath);
311
                        
312
                    }
313

    
314
                    //}
315
                    //System.Diagnostics.Debug.WriteLine("Download : " + result.LocalFilePath);
316
                }
317
            }
318
            catch (Exception ex)
319
            {
320
                throw new Exception("DownloadPageAsync : ", ex);
321
            }
322
            finally
323
            {
324
                IsDownload = false;
325
            }
326

    
327
            return result;
328
        }
329

    
330
        public void Clear()
331
        {
332
            try
333
            {
334
                ResetImage();
335
            }
336
            catch (Exception ex)
337
            {
338
                System.Diagnostics.Debug.WriteLine(ex.ToString());
339
            }
340

    
341
            try
342
            {
343
                backgroundWorker.CancelAsync();
344
                backgroundWorker.Dispose();
345

    
346
                foreach (var item in fileItems)
347
                {
348
                    System.IO.File.Delete(item.LocalFilePath);
349
                }
350

    
351
                System.IO.Directory.Delete(_localStorage, true);
352
            }
353
            catch (Exception ex)
354
            {
355
                System.Diagnostics.Debug.WriteLine(ex.ToString());
356
            }
357
        }
358
    }
359
}
클립보드 이미지 추가 (최대 크기: 500 MB)