OSDN Git Service

SlimDX から SharpDX へ機械的に移行。
[dtxmania/dtxmania.git] / DTXManiaプロジェクト / コード / ステージ / 05.選曲 / CActSelectPopupMenu.cs
1 using System;\r
2 using System.Collections.Generic;\r
3 using System.Diagnostics;\r
4 using System.Globalization;\r
5 using System.Text;\r
6 using System.Runtime.InteropServices;\r
7 using System.Drawing;\r
8 using System.IO;\r
9 using FDK;\r
10 \r
11 \r
12 namespace DTXMania\r
13 {\r
14         internal class CActSelectPopupMenu : CActivity\r
15         {\r
16                 // プロパティ\r
17                 public int GetIndex(int pos)\r
18                 {\r
19                         return lciMenuItems[pos].cItem.Index;\r
20                 }\r
21 \r
22                 public COptionBase GetObj現在値(int pos)\r
23                 {\r
24                         return lciMenuItems[pos].cItem;\r
25                 }\r
26 \r
27                 public bool bGotoDetailConfig\r
28                 {\r
29                         get;\r
30                         internal set;\r
31                 }\r
32 \r
33                 /// <summary>\r
34                 /// ポップアップメニュー機能を使用中かどうか。\r
35                 /// 外部からこれをtrueにすると、ポップアップメニューが出現する。falseにすると消える。\r
36                 /// </summary>\r
37                 public bool bIsActivePopupMenu\r
38                 {\r
39                         get;\r
40                         private set;\r
41                 }\r
42 \r
43                 public virtual void tActivatePopupMenu(EPart einst)\r
44                 {\r
45                         nItemSelecting = -1;        // #24757 2011.4.1 yyagi: Clear sorting status in each stating menu.\r
46                         this.eInst = einst;\r
47                         this.bIsActivePopupMenu = true;\r
48                         this.bIsSelectingIntItem = false;\r
49                         this.bGotoDetailConfig = false;\r
50                 }\r
51                 public virtual void tDeativatePopupMenu()\r
52                 {\r
53                         this.bIsActivePopupMenu = false;\r
54                 }\r
55 \r
56                 public void Initialize(List<COptionBase> menulist, bool showAllItems, string title, int defaultPos = 0)\r
57                 {\r
58 \r
59                         prvFont = new CPrivateFastFont(CSkin.Path(@"Graphics\fonts\mplus-1p-heavy.ttf"), (int)(18 * Scale.Y));\r
60 \r
61                         stqMenuTitle = new stQuickMenuItem();\r
62                         stqMenuTitle.cItem = new COptionString(title);\r
63                         stqMenuTitle.cItem.label = title;\r
64                         stqMenuTitle.txName = TextureFactory.tテクスチャの生成(prvFont.DrawPrivateFont(title, Color.White, Color.Black), false);\r
65                         stqMenuTitle.rectName = prvFont.RectStrings;\r
66                         lciMenuItems = new stQuickMenuItem[menulist.Count];\r
67                         for (int i = 0; i < menulist.Count; i++)\r
68                         {\r
69                                 stQuickMenuItem stqm = new stQuickMenuItem();\r
70                                 stqm.cItem = menulist[i];\r
71                                 stqm.txName = TextureFactory.tテクスチャの生成(prvFont.DrawPrivateFont(menulist[i].label, Color.White, Color.Black), false);\r
72                                 stqm.rectName = prvFont.RectStrings;\r
73                                 lciMenuItems[i] = stqm;\r
74                         }\r
75 \r
76                         bShowAllItems = showAllItems;\r
77                         n現在の選択行 = defaultPos;\r
78                 }\r
79 \r
80 \r
81                 public void tEnter押下()\r
82                 {\r
83                         if (this.bキー入力待ち)\r
84                         {\r
85                                 CDTXMania.Instance.Skin.sound決定音.t再生する();\r
86 \r
87                                 if (this.n現在の選択行 != lciMenuItems.Length - 1)\r
88                                 {\r
89                                         if (lciMenuItems[n現在の選択行].cItem is IOptionList ||\r
90                                                         lciMenuItems[n現在の選択行].cItem is COptionBool)\r
91                                         {\r
92                                                 lciMenuItems[n現在の選択行].cItem.OnNext();\r
93                                         }\r
94                                         else if (lciMenuItems[n現在の選択行].cItem is COptionInteger)\r
95                                         {\r
96                                                 bIsSelectingIntItem = !bIsSelectingIntItem;     // 選択状態/選択解除状態を反転する\r
97                                         }\r
98                                         nItemSelecting = n現在の選択行;\r
99                                 }\r
100                                 lciMenuItems[n現在の選択行].cItem.OnEnter();\r
101                                 this.bキー入力待ち = true;\r
102                         }\r
103                 }\r
104 \r
105                 /// <summary>\r
106                 /// 追加の描画処理。必要に応じて、継承先で記述する。\r
107                 /// </summary>\r
108                 public virtual void t進行描画sub()\r
109                 {\r
110                 }\r
111 \r
112                 public void t次に移動()\r
113                 {\r
114                         if (this.bキー入力待ち)\r
115                         {\r
116                                 CDTXMania.Instance.Skin.soundカーソル移動音.t再生する();\r
117                                 if (bIsSelectingIntItem)\r
118                                 {\r
119                                         // 項目移動と数値上下は方向が逆になるので注意\r
120                                         lciMenuItems[n現在の選択行].cItem.OnPrevious();\r
121                                 }\r
122                                 else\r
123                                 {\r
124                                         if (++this.n現在の選択行 >= this.lciMenuItems.Length)\r
125                                         {\r
126                                                 this.n現在の選択行 = 0;\r
127                                         }\r
128                                 }\r
129                         }\r
130                 }\r
131                 public void t前に移動()\r
132                 {\r
133                         if (this.bキー入力待ち)\r
134                         {\r
135                                 CDTXMania.Instance.Skin.soundカーソル移動音.t再生する();\r
136                                 if (bIsSelectingIntItem)\r
137                                 {\r
138                                         // 項目移動と数値上下は方向が逆になるので注意\r
139                                         lciMenuItems[n現在の選択行].cItem.OnNext();\r
140                                 }\r
141                                 else\r
142                                 {\r
143                                         if (--this.n現在の選択行 < 0)\r
144                                         {\r
145                                                 this.n現在の選択行 = this.lciMenuItems.Length - 1;\r
146                                         }\r
147                                 }\r
148                         }\r
149                 }\r
150 \r
151                 public override void On活性化()\r
152                 {\r
153                         this.n現在の選択行 = 0;\r
154                         this.bキー入力待ち = true;\r
155                         for (int i = 0; i < 4; i++)\r
156                         {\r
157                                 this.ctキー反復用[i] = new CCounter(0, 0, 0, CDTXMania.Instance.Timer);\r
158                         }\r
159                         base.b活性化してない = true;\r
160 \r
161                         this.bIsActivePopupMenu = false;\r
162                         nItemSelecting = -1;\r
163 \r
164 \r
165                         base.On活性化();\r
166                 }\r
167 \r
168                 public override void On非活性化()\r
169                 {\r
170                         if (!base.b活性化してない)\r
171                         {\r
172                                 //TextureFactory.tテクスチャの解放(ref this.txCursor);\r
173                                 //TextureFactory.tテクスチャの解放(ref this.txPopupMenuBackground);\r
174                                 for (int i = 0; i < 4; i++)\r
175                                 {\r
176                                         this.ctキー反復用[i] = null;\r
177                                 }\r
178                                 base.On非活性化();\r
179                         }\r
180                 }\r
181 \r
182                 public override void OnManagedリソースの作成()\r
183                 {\r
184                         if (!base.b活性化してない)\r
185                         {\r
186                                 string pathCursor = CSkin.Path(@"Graphics\ScreenConfig menu cursor.png"); ;\r
187                                 string pathPopupMenuBackground = CSkin.Path(@"Graphics\ScreenSelect sort menu background.png");\r
188                                 if (File.Exists(pathCursor))\r
189                                 {\r
190                                         this.txCursor = TextureFactory.tテクスチャの生成(pathCursor, false);\r
191                                 }\r
192                                 if (File.Exists(pathPopupMenuBackground))\r
193                                 {\r
194                                         this.txPopupMenuBackground = TextureFactory.tテクスチャの生成(pathPopupMenuBackground, false);\r
195                                 }\r
196                                 base.OnManagedリソースの作成();\r
197                         }\r
198                 }\r
199 \r
200                 public override void OnManagedリソースの解放()\r
201                 {\r
202                         if ( base.b活性化してる )\r
203                         {\r
204                                 TextureFactory.tテクスチャの解放( ref this.txPopupMenuBackground );\r
205                                 TextureFactory.tテクスチャの解放( ref this.txCursor );\r
206 \r
207                                 TextureFactory.tテクスチャの解放( ref stqMenuTitle.txName );\r
208                                 if ( lciMenuItems != null )\r
209                                 {\r
210                                         for ( int i = 0; i < lciMenuItems.Length; i++ )\r
211                                         {\r
212                                                 TextureFactory.tテクスチャの解放( ref lciMenuItems[i].txName );\r
213                                         }\r
214                                 }\r
215                         }\r
216                         base.OnManagedリソースの解放();\r
217                 }\r
218 \r
219                 public override int On進行描画()\r
220                 {\r
221                         throw new InvalidOperationException("t進行描画(bool)のほうを使用してください。");\r
222                 }\r
223 \r
224                 public int t進行描画()\r
225                 {\r
226                         if (!base.b活性化してない && this.bIsActivePopupMenu)\r
227                         {\r
228                                 if (this.bキー入力待ち)\r
229                                 {\r
230                                         #region [ Shift-F1: CONFIG画面 ]\r
231                                         if ((CDTXMania.Instance.Input管理.Keyboard.bキーが押されている((int)SharpDX.DirectInput.Key.RightShift) || CDTXMania.Instance.Input管理.Keyboard.bキーが押されている((int)SharpDX.DirectInput.Key.LeftShift)) &&\r
232                                                         CDTXMania.Instance.Input管理.Keyboard.bキーが押された((int)SharpDX.DirectInput.Key.F1))\r
233                                         {\r
234                                                 // [SHIFT] + [F1] CONFIG\r
235                                                 CDTXMania.Instance.Skin.sound取消音.t再生する();\r
236                                                 // tCancel();\r
237                                                 this.bGotoDetailConfig = true;\r
238                                         }\r
239                                         #endregion\r
240                                         #region [ キー入力: キャンセル ]\r
241                                         else if (CDTXMania.Instance.Input管理.Keyboard.bキーが押された((int)SharpDX.DirectInput.Key.Escape)\r
242                                                         || CDTXMania.Instance.Pad.bCancelPadIsPressedDGB())\r
243                                         {\r
244                                                 // キャンセル\r
245                                                 CDTXMania.Instance.Skin.sound取消音.t再生する();\r
246                                                 // tCancel();\r
247                                                 this.bIsActivePopupMenu = false;\r
248                                         }\r
249                                         #endregion\r
250 \r
251                                         #region [ キー入力: 決定 ]\r
252                                         // E楽器パート eInst = E楽器パート.UNKNOWN;\r
253                                         ESortAction eAction = ESortAction.END;\r
254                                         if (CDTXMania.Instance.Pad.b押された(EPad.GtDecide))\r
255                                         {\r
256                                                 eInst = EPart.Guitar;\r
257                                                 eAction = ESortAction.Decide;\r
258                                         }\r
259                                         else if (CDTXMania.Instance.Pad.b押された(EPad.BsDecide))\r
260                                         {\r
261                                                 eInst = EPart.Bass;\r
262                                                 eAction = ESortAction.Decide;\r
263                                         }\r
264                                         else if (\r
265                                                                  CDTXMania.Instance.Pad.b押された(EPad.CY) // #24756 2011.4.1 yyagi: Add condition "Drum-Decide" to enable CY in Sort Menu.\r
266                                                         || CDTXMania.Instance.Pad.b押された(EPad.RD)\r
267                                                         || CDTXMania.Instance.Pad.b押された(EPad.LC)\r
268                                                         || (CDTXMania.Instance.ConfigIni.bEnterがキー割り当てのどこにも使用されていない && CDTXMania.Instance.Input管理.Keyboard.bキーが押された((int)SharpDX.DirectInput.Key.Return)))\r
269                                         {\r
270                                                 eInst = EPart.Drums;\r
271                                                 eAction = ESortAction.Decide;\r
272                                         }\r
273                                         if (eAction == ESortAction.Decide)  // 決定\r
274                                         {\r
275                                                 this.tEnter押下();\r
276                                         }\r
277                                         #endregion\r
278                                         #region [ キー入力: 前に移動 ]\r
279                                         this.ctキー反復用.Up.tキー反復(CDTXMania.Instance.Input管理.Keyboard.bキーが押されている((int)SharpDX.DirectInput.Key.Up), new CCounter.DGキー処理(this.t前に移動));\r
280                                         this.ctキー反復用.R.tキー反復(CDTXMania.Instance.Pad.b押されている(EPad.GtR) || CDTXMania.Instance.Pad.b押されている(EPad.BsR), new CCounter.DGキー処理(this.t前に移動));\r
281                                         if (CDTXMania.Instance.Pad.b押された(EPad.SD))\r
282                                         {\r
283                                                 this.t前に移動();\r
284                                         }\r
285                                         #endregion\r
286                                         #region [ キー入力: 次に移動 ]\r
287                                         this.ctキー反復用.Down.tキー反復(CDTXMania.Instance.Input管理.Keyboard.bキーが押されている((int)SharpDX.DirectInput.Key.Down), new CCounter.DGキー処理(this.t次に移動));\r
288                                         this.ctキー反復用.B.tキー反復(CDTXMania.Instance.Pad.b押されている(EPad.GtB) || CDTXMania.Instance.Pad.b押されている(EPad.BsB), new CCounter.DGキー処理(this.t次に移動));\r
289                                         if (CDTXMania.Instance.Pad.b押された(EPad.LT))\r
290                                         {\r
291                                                 this.t次に移動();\r
292                                         }\r
293                                         #endregion\r
294                                 }\r
295                                 #region [ ポップアップ背景描画 ]\r
296                                 if (this.txPopupMenuBackground != null)\r
297                                 {\r
298                                         this.txPopupMenuBackground.t2D描画(CDTXMania.Instance.Device, 160 * Scale.X, 10 * Scale.Y);\r
299                                 }\r
300                                 #endregion\r
301                                 #region [ タイトル描画 ]\r
302                                 int x = (int)(240 * Scale.X), y = (int)(16 * Scale.Y);\r
303                                 stqMenuTitle.txName.t2D描画(CDTXMania.Instance.Device, x, y);\r
304                                 #endregion\r
305                                 #region [ カーソル描画 ]\r
306                                 if (this.txCursor != null)\r
307                                 {\r
308                                         int height = stqMenuTitle.rectName.Height;\r
309                                         int curX = (int)(180 * Scale.X);\r
310                                         int curY = (int)(16 * Scale.Y) + (height / 4 - 6) + (height * (this.n現在の選択行 + 1));\r
311                                         this.txCursor.t2D描画(CDTXMania.Instance.Device, curX, curY, new Rectangle(0, 0, (int)(16 * Scale.X), (int)(32 * Scale.Y)));\r
312                                         curX += (int)(0x10 * Scale.X);\r
313                                         Rectangle rectangle = new Rectangle((int)(8 * Scale.X), 0, (int)(0x10 * Scale.X), (int)(0x20 * Scale.Y));\r
314                                         for (int j = 0; j < 16 + 5; j++)\r
315                                         {\r
316                                                 this.txCursor.t2D描画(CDTXMania.Instance.Device, curX, curY, rectangle);\r
317                                                 curX += (int)(16 * Scale.Y);\r
318                                         }\r
319                                         this.txCursor.t2D描画(CDTXMania.Instance.Device, curX, curY, new Rectangle((int)(0x10 * Scale.X), 0, (int)(16 * Scale.X), (int)(32 * Scale.Y)));\r
320                                 }\r
321                                 #endregion\r
322                                 #region [ リスト値文字列描画 ]\r
323                                 for (int i = 0; i < lciMenuItems.Length; i++)\r
324                                 {\r
325                                         bool bItemBold = (i == nItemSelecting && !bShowAllItems) ? true : false;\r
326                                         if (lciMenuItems[i].txName != null)\r
327                                         {\r
328                                                 int height = lciMenuItems[i].rectName.Height;\r
329                                                 lciMenuItems[i].txName.t2D描画(CDTXMania.Instance.Device, 190 * Scale.X, (50 * Scale.Y) + i * height);\r
330                                         }\r
331 \r
332                                         bool bValueBold = (bItemBold || (i == nItemSelecting && bIsSelectingIntItem)) ? true : false;\r
333                                         if (bItemBold || bShowAllItems)\r
334                                         {\r
335                                                 string s = lciMenuItems[i].cItem.ToString();\r
336                                                 using (Bitmap bmpStr = bValueBold ?\r
337                                                                 prvFont.DrawPrivateFont(s, Color.White, Color.Black, Color.Yellow, Color.OrangeRed) :\r
338                                                                 prvFont.DrawPrivateFont(s, Color.White, Color.Black))\r
339                                                 {\r
340                                                         CTexture ctStr = TextureFactory.tテクスチャの生成(bmpStr, false);\r
341                                                         ctStr.t2D描画(CDTXMania.Instance.Device, 340 * Scale.X, (50 * Scale.Y) + i * prvFont.RectStrings.Height);\r
342                                                         TextureFactory.tテクスチャの解放(ref ctStr);\r
343                                                 }\r
344                                         }\r
345                                 }\r
346                                 #endregion\r
347                                 t進行描画sub();\r
348                         }\r
349                         return 0;\r
350                 }\r
351 \r
352 \r
353                 // その他\r
354 \r
355                 #region [ private ]\r
356                 //-----------------\r
357 \r
358                 private bool bキー入力待ち;\r
359 \r
360                 internal int n現在の選択行;\r
361                 internal EPart eInst = EPart.Unknown;\r
362 \r
363                 private CTexture txPopupMenuBackground;\r
364                 private CTexture txCursor;\r
365 \r
366                 internal struct stQuickMenuItem\r
367                 {\r
368                         internal COptionBase cItem;\r
369                         internal CTexture txName;\r
370                         internal Rectangle rectName;\r
371                 }\r
372                 private stQuickMenuItem[] lciMenuItems;\r
373                 CPrivateFastFont prvFont;\r
374 \r
375                 private stQuickMenuItem stqMenuTitle;\r
376                 private bool bShowAllItems;\r
377                 private bool bIsSelectingIntItem;\r
378 \r
379                 [StructLayout(LayoutKind.Sequential)]\r
380                 private struct STキー反復用カウンタ\r
381                 {\r
382                         public CCounter Up;\r
383                         public CCounter Down;\r
384                         public CCounter R;\r
385                         public CCounter B;\r
386                         public CCounter this[int index]\r
387                         {\r
388                                 get\r
389                                 {\r
390                                         switch (index)\r
391                                         {\r
392                                                 case 0:\r
393                                                         return this.Up;\r
394 \r
395                                                 case 1:\r
396                                                         return this.Down;\r
397 \r
398                                                 case 2:\r
399                                                         return this.R;\r
400 \r
401                                                 case 3:\r
402                                                         return this.B;\r
403                                         }\r
404                                         throw new IndexOutOfRangeException();\r
405                                 }\r
406                                 set\r
407                                 {\r
408                                         switch (index)\r
409                                         {\r
410                                                 case 0:\r
411                                                         this.Up = value;\r
412                                                         return;\r
413 \r
414                                                 case 1:\r
415                                                         this.Down = value;\r
416                                                         return;\r
417 \r
418                                                 case 2:\r
419                                                         this.R = value;\r
420                                                         return;\r
421 \r
422                                                 case 3:\r
423                                                         this.B = value;\r
424                                                         return;\r
425                                         }\r
426                                         throw new IndexOutOfRangeException();\r
427                                 }\r
428                         }\r
429                 }\r
430                 private STキー反復用カウンタ ctキー反復用;\r
431 \r
432                 private enum ESortAction : int\r
433                 {\r
434                         Cancel, Decide, Previous, Next, END\r
435                 }\r
436                 // 「n現在の選択行」とは別に設ける。sortでメニュー表示直後にアイテムの中身を表示しないようにするため\r
437                 private int nItemSelecting;\r
438 \r
439                 //-----------------\r
440                 #endregion\r
441         }\r
442 }\r