・キー割り当てを以下のキーに対して可能にした
・プレビューをbmpなどの形式に対応
・カーソル移動の挙動を改善
・アクティブではない方のビューも選択状態がうっすらと見えるように変更
@@ -347,6 +347,13 @@ | ||
347 | 347 | validKeys.Add(Keys.Oem5, "\\"); |
348 | 348 | validKeys.Add(Keys.Left,"Left"); |
349 | 349 | validKeys.Add(Keys.Right,"Right"); |
350 | + validKeys.Add(Keys.Up, "Up"); | |
351 | + validKeys.Add(Keys.Down, "Down"); | |
352 | + validKeys.Add(Keys.PageUp, "PageUp"); | |
353 | + validKeys.Add(Keys.PageDown, "PageDown"); | |
354 | + validKeys.Add(Keys.Home, "Home"); | |
355 | + validKeys.Add(Keys.End, "End"); | |
356 | + validKeys.Add(Keys.Insert, "Ins"); | |
350 | 357 | validKeys.Add(Keys.F1, "F1"); |
351 | 358 | validKeys.Add(Keys.F2, "F2"); |
352 | 359 | validKeys.Add(Keys.F3, "F3"); |
@@ -59,10 +59,14 @@ | ||
59 | 59 | } else if (info.FieldType == typeof(Color)) { |
60 | 60 | info.SetValue(instance, Color.FromArgb(int.Parse(value))); |
61 | 61 | } else if (info.FieldType == typeof(List<string>)) { |
62 | - info.SetValue(instance, Util.StringUtil.GetListFromConnectedString(value, new char[]{';'})); | |
62 | + info.SetValue(instance, Util.StringUtil.GetListFromConnectedString(value, new char[] { ';' })); | |
63 | + } else if (info.FieldType.IsEnum) { | |
64 | + info.SetValue(instance, Enum.Parse(info.FieldType, value)); | |
63 | 65 | } |
64 | 66 | } catch (FormatException) { |
65 | 67 | //parseに失敗した時は何もしない(デフォルト値を使う) |
68 | + } catch (ArgumentException) { | |
69 | + //同じくArgumentExceptionの時も何もしない(デフォルト値を使う) | |
66 | 70 | } |
67 | 71 | } |
68 | 72 | } |
@@ -15,7 +15,9 @@ | ||
15 | 15 | using SCFiler2.ViewInterface; |
16 | 16 | using SCFiler2.ItemInterface; |
17 | 17 | using SCFiler2.EventInterface; |
18 | +using System.Runtime.InteropServices; | |
18 | 19 | |
20 | + | |
19 | 21 | namespace SCFiler2 { |
20 | 22 | /// <summary> |
21 | 23 | /// ファイル一覧を表示するためのビュー(SCFilerのメインとなるビュー) |
@@ -88,6 +90,7 @@ | ||
88 | 90 | |
89 | 91 | public FileView() { |
90 | 92 | InitializeComponent(); |
93 | + ((CustomListView)this.listView).FocusChanged = new ListViewFocusChangedDelegate(this.focusChangedEvent); | |
91 | 94 | } |
92 | 95 | |
93 | 96 | /// <summary> |
@@ -177,12 +180,23 @@ | ||
177 | 180 | |
178 | 181 | |
179 | 182 | #region プレビュー関係 |
183 | + | |
184 | + private IFilerItem previewingItem = null; //現在表示中のアイテム | |
185 | + | |
180 | 186 | /// <summary> |
181 | 187 | /// プレビュー領域にtargetItemを描画する(今は画像のプレビューのみ) |
182 | 188 | /// </summary> |
183 | 189 | /// <param name="targetItem"></param> |
184 | 190 | public void drawPreview(IFilerItem targetItem) { |
191 | + if (previewingItem != null && previewingItem.FullName == targetItem.FullName) { | |
192 | + return; | |
193 | + } | |
194 | + | |
185 | 195 | Bitmap srcBitmap = susie.GetPicture(targetItem.FullName); |
196 | + if (srcBitmap == null) { | |
197 | + srcBitmap = (Bitmap)Bitmap.FromFile(targetItem.FullName); | |
198 | + } | |
199 | + | |
186 | 200 | if (srcBitmap != null) { |
187 | 201 | Bitmap displayBitmap; |
188 | 202 | //サイズがListViewより大きかったらサイズを合わせる |
@@ -208,6 +222,8 @@ | ||
208 | 222 | previewPictureBox.Image = displayBitmap; |
209 | 223 | previewPictureBox.Refresh(); |
210 | 224 | SCFiler2System.ShowTempMessage(targetItem.FullName); |
225 | + | |
226 | + previewingItem = targetItem; | |
211 | 227 | } else { |
212 | 228 | previewPictureBox.Image = null;//画像を消去 |
213 | 229 | SCFiler2System.ShowTempMessage("この形式はプレビューできません"); |
@@ -215,6 +231,7 @@ | ||
215 | 231 | } |
216 | 232 | |
217 | 233 | public void exitPreview() { |
234 | + previewingItem = null; | |
218 | 235 | } |
219 | 236 | |
220 | 237 | #endregion プレビュー関係 |
@@ -556,6 +573,8 @@ | ||
556 | 573 | return; |
557 | 574 | case ListViewController.Result.EventNotHandled: |
558 | 575 | break; //何もしないで、続く処理に移る |
576 | + case ListViewController.Result.DelegateToOriginalControl: | |
577 | + return; //コントロールの処理に任せる | |
559 | 578 | } |
560 | 579 | |
561 | 580 | //数字キーでドライブ移動 |
@@ -587,10 +606,9 @@ | ||
587 | 606 | return; |
588 | 607 | case ListViewController.Result.EventNotHandled: |
589 | 608 | break; |
609 | + case ListViewController.Result.DelegateToOriginalControl: | |
610 | + return; | |
590 | 611 | } |
591 | - | |
592 | - //何も実行できなくても、デフォルトの動作をしないようにHandledはtrueを返す | |
593 | - e.Handled = true; | |
594 | 612 | } |
595 | 613 | |
596 | 614 | /// <summary> |
@@ -1084,5 +1102,18 @@ | ||
1084 | 1102 | } |
1085 | 1103 | |
1086 | 1104 | #endregion |
1105 | + | |
1106 | + private void listView_ItemSelectionChanged(object sender, ListViewItemSelectionChangedEventArgs e) { | |
1107 | + | |
1108 | + } | |
1109 | + | |
1110 | + private void listView_ItemActivate(object sender, EventArgs e) { | |
1111 | + } | |
1112 | + | |
1113 | + private void focusChangedEvent(int index) { | |
1114 | + if (this.viewMode == ViewMode.ListInPreviewMode) { | |
1115 | + MainForm.Instance.GetAnotherFileView(this).drawPreview(this.virtualListView.FocusedItem.FilerItem); | |
1116 | + } | |
1117 | + } | |
1087 | 1118 | } |
1088 | 1119 | } |
@@ -86,55 +86,19 @@ | ||
86 | 86 | return Result.EventNotHandled; |
87 | 87 | } |
88 | 88 | |
89 | - //十時キーの上下、PageUp/Downを処理する | |
90 | - if (allItemSearcher.ContainsKey(ItemSearcher.SearchType.Basic)) { | |
91 | - ItemSearcher searcher = allItemSearcher[ItemSearcher.SearchType.Basic]; | |
92 | - ItemSearcher.Result result = searcher.KeyDown(keyEvent); | |
93 | - switch (result) { | |
94 | - case ItemSearcher.Result.ItemFound: | |
95 | - if (keyEvent.Shift && !keyEvent.Alt && !keyEvent.Control) { //Shiftキーが押されていた時 | |
96 | - SelectingMove(searcher.FoundItem); | |
97 | - } else if (!keyEvent.Shift && !keyEvent.Alt && keyEvent.Control) { | |
98 | - OnlyFocusMove(searcher.FoundItem); | |
99 | - } else { | |
100 | - SimpleMove(searcher.FoundItem); | |
101 | - } | |
102 | - return Result.EventHandled; | |
103 | - case ItemSearcher.Result.ItemNotFound: | |
104 | - return Result.EventHandled; | |
105 | - } | |
106 | - } | |
107 | - | |
108 | 89 | //頭文字サーチ |
109 | 90 | if (allItemSearcher.ContainsKey(ItemSearcher.SearchType.Prefix)) { |
110 | - ItemSearcher searcher = allItemSearcher[ItemSearcher.SearchType.Prefix]; | |
111 | - ItemSearcher.Result result = searcher.KeyDown(keyEvent); | |
112 | - switch (result) { | |
113 | - case ItemSearcher.Result.ItemFound: | |
114 | - SimpleMove(searcher.FoundItem); | |
115 | - return Result.EventHandled; | |
116 | - case ItemSearcher.Result.ItemNotFound: | |
117 | - return Result.EventHandled; | |
118 | - } | |
91 | + ItemSearcher searcher = allItemSearcher[ItemSearcher.SearchType.Prefix]; | |
92 | + ItemSearcher.Result result = searcher.KeyDown(keyEvent); | |
93 | + switch (result) { | |
94 | + case ItemSearcher.Result.ItemFound: | |
95 | + SimpleMove(searcher.FoundItem); | |
96 | + return Result.EventHandled; | |
97 | + case ItemSearcher.Result.ItemNotFound: | |
98 | + return Result.EventHandled; | |
99 | + } | |
119 | 100 | } |
120 | 101 | |
121 | - //このコントローラー特有の処理 | |
122 | - //スペースが押されたら選択状態を反転 | |
123 | - switch (keyEvent.KeyCode) { | |
124 | - case Keys.Space: | |
125 | - if (keyEvent.Shift) { | |
126 | - SelectingMove(targetListView.FocusedItem); | |
127 | - return Result.EventHandled; | |
128 | - } else { | |
129 | - if (targetListView.SelectedItems.Count == 1) { | |
130 | - //選択アイテムがなくなるのを防ぐ | |
131 | - break; | |
132 | - } | |
133 | - targetListView.FocusedItem.Selected = !targetListView.FocusedItem.Selected; //選択状態を反転 | |
134 | - return Result.EventHandled; | |
135 | - } | |
136 | - } | |
137 | - | |
138 | 102 | return Result.EventNotHandled; |
139 | 103 | } |
140 | 104 |
@@ -35,7 +35,7 @@ | ||
35 | 35 | this.appName.Name = "appName"; |
36 | 36 | this.appName.Size = new System.Drawing.Size(147, 12); |
37 | 37 | this.appName.TabIndex = 0; |
38 | - this.appName.Text = "SCFiler2 Alpha version 0.38"; | |
38 | + this.appName.Text = "SCFiler2 Alpha version 0.39"; | |
39 | 39 | this.appName.Click += new System.EventHandler(this.appName_Click); |
40 | 40 | // |
41 | 41 | // okButton |
@@ -48,6 +48,7 @@ | ||
48 | 48 | SelectAll, |
49 | 49 | RefleshAll, |
50 | 50 | PreviewMode, |
51 | + ThumbnailMode, | |
51 | 52 | Sort, |
52 | 53 | SwitchNarrowDownMode, |
53 | 54 |
@@ -156,6 +157,8 @@ | ||
156 | 157 | return new RefleshAll(); |
157 | 158 | case ActionID.PreviewMode: |
158 | 159 | return new PreviewMode(); |
160 | + case ActionID.ThumbnailMode: | |
161 | + return new ThumbnailMode(); | |
159 | 162 | case ActionID.Sort: |
160 | 163 | return new Sort(); |
161 | 164 | case ActionID.SwitchNarrowDownMode: |
@@ -10,6 +10,34 @@ | ||
10 | 10 | : base(parentView, targetListView) { |
11 | 11 | } |
12 | 12 | |
13 | + //ListViewのアイテムが2列以上あるかどうか(左右に移動できるかどうか)で使い分ける | |
14 | + static private Dictionary<Keys, string> exchangeListAtDetailView = new Dictionary<Keys, string>(); | |
15 | + static private Dictionary<Keys, string> exchangeListAtThumbnailView = new Dictionary<Keys, string>(); | |
16 | + Dictionary<Keys, string> exchangeList; | |
17 | + | |
18 | + /// <summary> | |
19 | + /// スタティックイニシャライザ | |
20 | + /// </summary> | |
21 | + static EasySelectListViewController() { | |
22 | + exchangeListAtDetailView.Add(Keys.Up, "^{UP}"); | |
23 | + exchangeListAtDetailView.Add(Keys.Down, "^{DOWN}"); | |
24 | + exchangeListAtDetailView.Add(Keys.PageUp, "^{PGUP}"); | |
25 | + exchangeListAtDetailView.Add(Keys.PageDown, "^{PGDN}"); | |
26 | + exchangeListAtDetailView.Add(Keys.Home, "^{HOME}"); | |
27 | + exchangeListAtDetailView.Add(Keys.End, "^{END}"); | |
28 | + exchangeListAtDetailView.Add(Keys.Space, "^( {DOWN})"); | |
29 | + | |
30 | + exchangeListAtThumbnailView.Add(Keys.Up, "^{UP}"); | |
31 | + exchangeListAtThumbnailView.Add(Keys.Down, "^{DOWN}"); | |
32 | + exchangeListAtThumbnailView.Add(Keys.Right, "^{RIGHT}"); | |
33 | + exchangeListAtThumbnailView.Add(Keys.Left, "^{LEFT}"); | |
34 | + exchangeListAtThumbnailView.Add(Keys.PageUp, "^{PGUP}"); | |
35 | + exchangeListAtThumbnailView.Add(Keys.PageDown, "^{PGDN}"); | |
36 | + exchangeListAtThumbnailView.Add(Keys.Home, "^{HOME}"); | |
37 | + exchangeListAtThumbnailView.Add(Keys.End, "^{END}"); | |
38 | + exchangeListAtThumbnailView.Add(Keys.Space, "^( {DOWN})"); | |
39 | + } | |
40 | + | |
13 | 41 | public override void Initialize() { |
14 | 42 | SCFiler2System.ShowTempMessage("スペースキーで選択モード"); |
15 | 43 | //デフォルトで持っているItemSearcher |
@@ -16,13 +44,15 @@ | ||
16 | 44 | allItemSearcher.Add(ItemSearcher.SearchType.Basic, new BasicItemSearcher(this, targetListView)); |
17 | 45 | allItemSearcher.Add(ItemSearcher.SearchType.Prefix, new PrefixItemSearcher(this, targetListView)); |
18 | 46 | |
19 | - //すでに選択済みだったらフォーカスを一つ下へ | |
20 | - if (targetListView.FocusedItem.Selected) { | |
21 | - int newIndex = targetListView.FocusedItem.Index + 1; | |
22 | - if (newIndex < targetListView.Items.Count) { | |
23 | - targetListView.Items[newIndex].Focused = true; | |
24 | - } | |
47 | + this.exchangeList = (this.parentView.ViewMode == ViewMode.ThumbnailMode) ? exchangeListAtThumbnailView : exchangeListAtDetailView; | |
48 | + | |
49 | + //現在のアイテムを選択状態にして一つ下に移動する | |
50 | + if (this.targetListView.FocusedItem.Selected) { | |
51 | + SendKeys.Send(exchangeListAtDetailView[Keys.Down]); | |
52 | + } else { | |
53 | + SendKeys.Send(exchangeListAtDetailView[Keys.Space]); | |
25 | 54 | } |
55 | + | |
26 | 56 | } |
27 | 57 | public override void Terminate() { |
28 | 58 | //全てのsearcherを終わらせる |
@@ -47,6 +77,10 @@ | ||
47 | 77 | } |
48 | 78 | |
49 | 79 | override public Result KeyProcessingBeforeKeyCommand(KeyEventArgs keyEvent) { |
80 | + if (this.exchangeList.ContainsKey(keyEvent.KeyCode) && keyEvent.Control) { | |
81 | + return Result.DelegateToOriginalControl; | |
82 | + } | |
83 | + | |
50 | 84 | //incremental search, Migemo |
51 | 85 | ItemSearcher searcher = null; |
52 | 86 | if (allItemSearcher.ContainsKey(ItemSearcher.SearchType.Incremental)) { |
@@ -69,19 +103,13 @@ | ||
69 | 103 | } |
70 | 104 | } |
71 | 105 | |
72 | - //このController独自の処理 | |
73 | - //スペースを押したら選択状態を反転 | |
74 | - if (this.targetListView.Items.Count != 0 && keyEvent.KeyCode == Keys.Space && !keyEvent.Shift && !keyEvent.Alt && !keyEvent.Control) { | |
75 | - targetListView.FocusedItem.Selected = !targetListView.FocusedItem.Selected; //反転 | |
76 | - //選択したら次のアイテムに移る | |
77 | - int newFocusIndex = targetListView.FocusedItem.Index + 1; | |
78 | - if (newFocusIndex < targetListView.Items.Count) { | |
79 | - targetListView.Items[newFocusIndex].Focused = true; | |
80 | - parentView.FocusedItemChanged(); | |
81 | - } | |
106 | + //上下左右キーなどはキーイベントを変換して発行する(コントロールオリジナルの制御を生かしてキーのみ入れ替える) | |
107 | + if (this.targetListView.Items.Count != 0 && !keyEvent.Shift && !keyEvent.Control && !keyEvent.Alt && exchangeListAtDetailView.ContainsKey(keyEvent.KeyCode)) { | |
108 | + SendKeys.Send(exchangeList[keyEvent.KeyCode]); | |
82 | 109 | return Result.EventHandled; |
83 | 110 | } |
84 | 111 | |
112 | + | |
85 | 113 | //Escapeが押されたら終了(NormalControllerに戻す) |
86 | 114 | if (keyEvent.KeyCode == Keys.Escape && !keyEvent.Control && !keyEvent.Alt && !keyEvent.Shift) { |
87 | 115 | return Result.ExitCurrentController; |
@@ -92,24 +120,11 @@ | ||
92 | 120 | } |
93 | 121 | |
94 | 122 | override public Result KeyProcessingAfterKeyCommand(KeyEventArgs keyEvent) { |
95 | - //ビューにアイテムがないときは何もしない | |
123 | + //アイテムが0の時は何もしない | |
96 | 124 | if (this.targetListView.Items.Count == 0) { |
97 | 125 | return Result.EventNotHandled; |
98 | 126 | } |
99 | 127 | |
100 | - //上下キー、PageUp/Downの処理 | |
101 | - if (allItemSearcher.ContainsKey(ItemSearcher.SearchType.Basic)) { | |
102 | - ItemSearcher searcher = allItemSearcher[ItemSearcher.SearchType.Basic]; | |
103 | - ItemSearcher.Result result = searcher.KeyDown(keyEvent); | |
104 | - switch (result) { | |
105 | - case ItemSearcher.Result.ItemFound: | |
106 | - base.OnlyFocusMove(searcher.FoundItem); | |
107 | - return Result.EventHandled; | |
108 | - case ItemSearcher.Result.ItemNotFound: | |
109 | - return Result.EventHandled; | |
110 | - } | |
111 | - } | |
112 | - | |
113 | 128 | //頭文字サーチ |
114 | 129 | if (allItemSearcher.ContainsKey(ItemSearcher.SearchType.Prefix)) { |
115 | 130 | ItemSearcher searcher = allItemSearcher[ItemSearcher.SearchType.Prefix]; |
@@ -116,13 +131,13 @@ | ||
116 | 131 | ItemSearcher.Result result = searcher.KeyDown(keyEvent); |
117 | 132 | switch (result) { |
118 | 133 | case ItemSearcher.Result.ItemFound: |
119 | - base.OnlyFocusMove(searcher.FoundItem); | |
134 | + SimpleMove(searcher.FoundItem); | |
120 | 135 | return Result.EventHandled; |
121 | 136 | case ItemSearcher.Result.ItemNotFound: |
122 | 137 | return Result.EventHandled; |
123 | 138 | } |
124 | 139 | } |
125 | - //どれにも引っかからなかったときは処理しなかったことにする | |
140 | + | |
126 | 141 | return Result.EventNotHandled; |
127 | 142 | } |
128 | 143 |
@@ -14,7 +14,6 @@ | ||
14 | 14 | private FilerItem targetItem; |
15 | 15 | private ListViewItem viewItem; |
16 | 16 | private VirtualListView parentView; |
17 | - private bool focused; | |
18 | 17 | private string text; |
19 | 18 | private object tag; |
20 | 19 |
@@ -24,7 +23,6 @@ | ||
24 | 23 | /// <param name="fierItem">このアイテムに関連付けるアイテムのFullName</param> |
25 | 24 | public VirtualListViewItem(FilerItem filerItem) { |
26 | 25 | this.targetItem = filerItem; |
27 | - this.focused = false; | |
28 | 26 | this.tag = filerItem; |
29 | 27 | text = filerItem.NameWithoutExtension; |
30 | 28 | } |
@@ -92,30 +90,20 @@ | ||
92 | 90 | /// </summary> |
93 | 91 | public bool Focused { |
94 | 92 | set { |
95 | - if (this.focused == value) { | |
96 | - if (this.viewItem != null) { | |
97 | - this.viewItem.Focused = value; | |
98 | - } | |
99 | - return; //何もしない | |
100 | - } | |
101 | - //リストビューに反映 | |
102 | - if (value == true) { | |
103 | - if (this.parentView.FocusedItem != null) { | |
104 | - this.parentView.FocusedItem.focused = false; | |
105 | - } | |
106 | - this.parentView.FocusedItem = this; | |
107 | - } else { | |
108 | - this.parentView.FocusedItem = null; | |
109 | - } | |
110 | - //すでにListViewのアイテムがあるときはそれも変更 | |
111 | 93 | if (this.viewItem != null) { |
112 | 94 | this.viewItem.Focused = value; |
95 | + } else { | |
96 | + this.createListViewItem(); | |
97 | + this.viewItem.Focused = value; | |
113 | 98 | } |
114 | - this.focused = value; | |
115 | 99 | } |
116 | 100 | |
117 | 101 | get { |
118 | - return this.focused; | |
102 | + if (this.viewItem == null) { | |
103 | + return false; | |
104 | + } else { | |
105 | + return this.viewItem.Focused; | |
106 | + } | |
119 | 107 | } |
120 | 108 | } |
121 | 109 |
@@ -218,7 +206,6 @@ | ||
218 | 206 | this.viewItem.SubItems.Add(this.targetItem.SizeDisplayString);//サイズ列 |
219 | 207 | this.viewItem.SubItems.Add(this.targetItem.UpdateDateString);//更新日列 |
220 | 208 | this.viewItem.Tag = this.targetItem; |
221 | - this.viewItem.Focused = this.Focused; | |
222 | 209 | this.viewItem.Selected = this.Selected; |
223 | 210 | } |
224 | 211 |
@@ -1,8 +1,25 @@ | ||
1 | 1 | 更新履歴 |
2 | 2 | |
3 | +■0.39 | |
4 | +・キー割り当てを以下のキーに対して可能にした | |
5 | + 矢印上下、Home, End, PageUp, PageDown, insert | |
6 | + 制約として、Ctrl+矢印およびCtrl+スペースキーに割り当てた機能は、「スペースで選択」モードではキーが効きません | |
7 | +・プレビューをbmpなどの形式に対応 | |
8 | +・カーソル移動の挙動を改善 | |
9 | + 実装を大幅に変更。いくつかの変な動きが改善されていると思います。 | |
10 | + これまでと挙動が変わることがあるのでご注意ください。 | |
11 | + また、代わりにバグが入っている可能性もあるので見つけたらご連絡ください。 | |
12 | +・アクティブではない方のビューの選択状態がわかる(うっすらと色が付く)ようにした | |
13 | + | |
14 | +■0.38.1 | |
15 | + 0.38で追加したアイコンの設定が、SCFiler2を再起動したら元に戻る不具合を修正しました。 | |
16 | + (オプションで設定してすぐは反映されず、次にフォルダを移動して初めて反映されるのはそのうち修正します) | |
17 | + | |
3 | 18 | ■0.38 |
4 | 19 | ・フォルダ以外のアイコンも表示可能にした |
5 | 20 | 設定ダイアログの表示タブに設定項目があります |
21 | +・ビューに表示アイテムがない状態でキー操作で落ちるパターンを何個か修正 | |
22 | +・プラグインのI/Fを修正(プラグインによっては要最新版への更新) | |
6 | 23 | |
7 | 24 | ■0.37 |
8 | 25 | ・プラグインにキー割り当てを可能にした |
@@ -23,6 +23,10 @@ | ||
23 | 23 | /// このコントローラを終了するというコマンドが入力された |
24 | 24 | /// </summary> |
25 | 25 | ExitCurrentController, |
26 | + /// <summary> | |
27 | + /// このコントロールやアクションでは処理せず、コントロールのオリジナルの実装にキー処理を任せることを指示する | |
28 | + /// </summary> | |
29 | + DelegateToOriginalControl, | |
26 | 30 | } |
27 | 31 | |
28 | 32 | public ListViewController(FileView parentView, VirtualListView targetView) { |
@@ -0,0 +1,54 @@ | ||
1 | +using System; | |
2 | +using System.Collections.Generic; | |
3 | +using System.Text; | |
4 | +using System.Windows.Forms; | |
5 | +using System.Runtime.InteropServices; | |
6 | + | |
7 | +namespace SCFiler2 { | |
8 | + delegate void ListViewFocusChangedDelegate(int index); | |
9 | + | |
10 | + /// <summary> | |
11 | + /// リストビューにフォーカス移動イベントを追加するためのクラス | |
12 | + /// </summary> | |
13 | + class CustomListView : ListView { | |
14 | + internal ListViewFocusChangedDelegate FocusChanged = null; | |
15 | + | |
16 | + //このメソッドの実装は | |
17 | + //http://hongliang.seesaa.net/article/16550502.html | |
18 | + //で公開されているコードを使用させていただきました | |
19 | + protected override void WndProc(ref Message m) { | |
20 | + // LVN_ITEMCHANGED は親フォームに WM_NOTIFY(0x4E)で送信され、 | |
21 | + // 親フォームはそれを該当コントロールに | |
22 | + // WM_REFLECT(WM_USER(0x400)+0x1C00) を追加したメッセージコードで通知する。 | |
23 | + const int ReflectedItemChanged = 0x400 + 0x1c00 + 0x4e; | |
24 | + // LVN_ITEMCHANGED | |
25 | + const int ItemChanged = -101; | |
26 | + // NMHDR / NMLISTVIEW 構造体におけるメンバのオフセット(先頭の hdr 除く) | |
27 | + const int OffsetCode = 4, OffsetIndex = 8, OffsetState = 16; | |
28 | + if (m.Msg == ReflectedItemChanged) { | |
29 | + // LPARAM を NMHDR に見立てて通知コード(code)を取得 | |
30 | + int code = Marshal.ReadInt32(m.LParam, IntPtr.Size + OffsetCode); | |
31 | + if (code == ItemChanged) { | |
32 | + // LPARAM を NMLISTVIEW に見立ててアイテムの状態(uNewState)を取得 | |
33 | + int state = Marshal.ReadInt32(m.LParam, IntPtr.Size + OffsetState); | |
34 | + const int Focused = 1; | |
35 | + // 最下位ビットが立っている場合フォーカスが存在すると言う意味になる | |
36 | + // フォーカスがアイテム 1 からアイテム 2 に動いた場合、 | |
37 | + // ItemChanged は複数回送られる。 | |
38 | + // 一般的に、アイテム 1 の選択解除、アイテム 1 のフォーカス解除、 | |
39 | + // アイテム 2 のフォーカスと選択状態の獲得、の順である。 | |
40 | + // アイテム 1 の状態については uOldState の方に現れるので、 | |
41 | + // state (uNewState) に出ることはない | |
42 | + if ((state & Focused) != 0) { | |
43 | + // LPARAM を NMLISTVIEW に見立ててインデックス(iItem)を取得 | |
44 | + int index = Marshal.ReadInt32(m.LParam, IntPtr.Size + OffsetIndex); | |
45 | + if (this.FocusChanged != null) { | |
46 | + this.FocusChanged(index); | |
47 | + } | |
48 | + } | |
49 | + } | |
50 | + } | |
51 | + base.WndProc(ref m); | |
52 | + } | |
53 | + } | |
54 | +} |
@@ -26,7 +26,8 @@ | ||
26 | 26 | this.driveInfoPanel = new System.Windows.Forms.Panel(); |
27 | 27 | this.folderInfoLabel = new System.Windows.Forms.Label(); |
28 | 28 | this.driveInfoLabel = new System.Windows.Forms.Label(); |
29 | - this.listView = new System.Windows.Forms.ListView(); | |
29 | + //this.listView = new System.Windows.Forms.ListView(); | |
30 | + this.listView = new CustomListView(); | |
30 | 31 | this.currentPathText = new System.Windows.Forms.TextBox(); |
31 | 32 | this.previewPictureBox = new System.Windows.Forms.PictureBox(); |
32 | 33 | this.fileSystemWatcher = new System.IO.FileSystemWatcher(); |
@@ -70,6 +71,8 @@ | ||
70 | 71 | // |
71 | 72 | this.listView.AllowDrop = true; |
72 | 73 | this.listView.FullRowSelect = true; |
74 | + this.listView.HideSelection = false; | |
75 | + this.listView.LabelWrap = false; | |
73 | 76 | this.listView.Location = new System.Drawing.Point(0, 19); |
74 | 77 | this.listView.Name = "listView"; |
75 | 78 | this.listView.Size = new System.Drawing.Size(79, 64); |
@@ -77,6 +80,7 @@ | ||
77 | 80 | this.listView.UseCompatibleStateImageBehavior = false; |
78 | 81 | this.listView.View = System.Windows.Forms.View.Details; |
79 | 82 | this.listView.VirtualMode = true; |
83 | + this.listView.ItemActivate += new System.EventHandler(this.listView_ItemActivate); | |
80 | 84 | this.listView.Resize += new System.EventHandler(this.listView_Resize); |
81 | 85 | this.listView.MouseClick += new System.Windows.Forms.MouseEventHandler(this.listView_MouseClick); |
82 | 86 | this.listView.SelectedIndexChanged += new System.EventHandler(this.listView_SelectedIndexChanged); |
@@ -86,6 +90,7 @@ | ||
86 | 90 | this.listView.DragDrop += new System.Windows.Forms.DragEventHandler(this.listView_DragDrop); |
87 | 91 | this.listView.ColumnClick += new System.Windows.Forms.ColumnClickEventHandler(this.listView_ColumnClick); |
88 | 92 | this.listView.RetrieveVirtualItem += new System.Windows.Forms.RetrieveVirtualItemEventHandler(this.listView_RetrieveVirtualItem); |
93 | + this.listView.ItemSelectionChanged += new System.Windows.Forms.ListViewItemSelectionChangedEventHandler(this.listView_ItemSelectionChanged); | |
89 | 94 | this.listView.DragEnter += new System.Windows.Forms.DragEventHandler(this.listView_DragEnter); |
90 | 95 | this.listView.KeyPress += new System.Windows.Forms.KeyPressEventHandler(this.listView_KeyPress); |
91 | 96 | this.listView.DragLeave += new System.EventHandler(this.listView_DragLeave); |
@@ -37,6 +37,11 @@ | ||
37 | 37 | /// プレビューモードの時のプレビュー部分担当 |
38 | 38 | /// </summary> |
39 | 39 | PreviewInPreviewMode, |
40 | + | |
41 | + /// <summary> | |
42 | + /// サムネイル表示 | |
43 | + /// </summary> | |
44 | + ThumbnailMode, | |
40 | 45 | } |
41 | 46 | |
42 | 47 | /// <summary> |