OSDN Git Service

b6bea9c245191c76fe92850bb847704ec21d01b7
[dtxmania/dtxmania.git] / DTXManiaプロジェクト / コード / ステージ / 04.コンフィグ / COption.cs
1 using System;\r
2 using System.Collections.Generic;\r
3 using System.Linq;\r
4 using System.Text;\r
5 using System.Threading.Tasks;\r
6 using System.Runtime.Serialization;\r
7 using System.Diagnostics;\r
8 using FDK;\r
9 \r
10 namespace DTXMania\r
11 {\r
12         public delegate void VoidFunc();\r
13 \r
14         /// <summary>\r
15         /// Option 基底クラス。\r
16         /// 注意:値の参照は Value プロパティを使ってください。\r
17         /// 一部のクラスは暗黙的な型変換を実装していますが、\r
18         /// オプションクラスインスタンス同士の等価比較には気をつけてください。\r
19         /// </summary>\r
20         [DataContract]\r
21         public abstract class COptionBase\r
22         {\r
23                 public EOptionType type;\r
24 \r
25                 private string _label;\r
26                 /// <summary>\r
27                 /// コンフィグ画面におけるこの項目を表す文字列。\r
28                 /// nullの場合は、代わりにstrnameで名づけられたリソースから文字列を取得します。\r
29                 /// </summary>\r
30                 public string label\r
31                 {\r
32                         get\r
33                         {\r
34                                 return (_label == null)? CDTXMania.Instance.Resources.Label(_strname ) : _label;\r
35                         }\r
36                         set\r
37                         {\r
38                                 _label = value;\r
39                                 _strname = null;\r
40                         }\r
41                 }\r
42 \r
43                 private string _explanation;\r
44                 /// <summary>\r
45                 /// 説明。\r
46                 /// nullの場合は、代わりにstrnameで名づけられたリソースから文字列を取得します。\r
47                 /// </summary>\r
48                 public string explanation\r
49                 {\r
50                         get\r
51                         {\r
52                                 return ( _explanation == null ) ? CDTXMania.Instance.Resources.Explanation( _strname ) : _explanation;\r
53                         }\r
54                         set\r
55                         {\r
56                                 _explanation = value;\r
57                                 _strname = null;\r
58                         }\r
59                 }\r
60 \r
61                 private string _strname;\r
62                 /// <summary>\r
63                 /// 文字列の名前。リソースから文字列を取得する場合のkey文字列として使用。\r
64                 /// これがnullの場合は、labelとexplanationに設定された文字列を直接使います。\r
65                 /// </summary>\r
66                 public string strname\r
67                 {\r
68                         get\r
69                         {\r
70                                 return _strname;\r
71                         }\r
72                         set\r
73                         {\r
74                                 _strname = value;\r
75                         }\r
76                 \r
77                 }\r
78 \r
79                 /// <summary>\r
80                 /// OnEnter で用いる動作。たとえば、この値によってほかのオプションに制約を与える場合などに\r
81                 /// その処理を登録しておけば、値の確定後実行されます。\r
82                 /// </summary>\r
83                 public VoidFunc OnEnterDelegate;\r
84 \r
85                 /// <summary>\r
86                 /// 決定動作。OnEnterDelegate メンバに動作を登録します。\r
87                 /// </summary>\r
88                 public void OnEnter()\r
89                 {\r
90                         if (OnEnterDelegate != null)\r
91                         {\r
92                                 OnEnterDelegate();\r
93                         }\r
94                 }\r
95 \r
96                 /// <summary>\r
97                 /// 前の項目値動作。順序付け可能な値からなるオプションは相応に実装する必要があります。\r
98                 /// </summary>\r
99                 public virtual void OnPrevious()\r
100                 {\r
101                 }\r
102 \r
103                 /// <summary>\r
104                 /// アイテムインデックス。\r
105                 /// </summary>\r
106                 public virtual int Index\r
107                 {\r
108                         get\r
109                         {\r
110                                 return 0;\r
111                         }\r
112                         set\r
113                         {\r
114 \r
115                         }\r
116                 }\r
117 \r
118                 /// <summary>\r
119                 /// OnPrevious の逆順序用。\r
120                 /// </summary>\r
121                 public virtual void OnNext()\r
122                 {\r
123                 }\r
124         }\r
125 \r
126         /// <summary>\r
127         /// Option 基底クラス。\r
128         /// DataContract により XML へのシリアライズ、XML からのデシリアライズが可能です。\r
129         /// </summary>\r
130         /// <typeparam name="T">このオプションの型。</typeparam>\r
131         [DataContract]\r
132         public abstract class COption<T> : COptionBase\r
133         {\r
134                 [DataMember]\r
135                 protected T val;\r
136 \r
137                 public virtual T Value\r
138                 {\r
139                         get\r
140                         {\r
141                                 return val;\r
142                         }\r
143                         set\r
144                         {\r
145                                 val = value;\r
146                         }\r
147                 }\r
148         }\r
149 \r
150         [DataContract]\r
151         public class COptionBool : COption<bool>\r
152         {\r
153                 public static implicit operator bool (COptionBool b)\r
154                 {\r
155                         return b.Value;\r
156                 }\r
157 \r
158                 public override int Index\r
159                 {\r
160                         get\r
161                         {\r
162                                 return val ? 1 : 0;\r
163                         }\r
164                 }\r
165 \r
166                 public COptionBool(bool init)\r
167                 {\r
168                         val = init;\r
169                 }\r
170 \r
171                 public override void OnNext()\r
172                 {\r
173                         OnPrevious();\r
174                 }\r
175 \r
176                 public override void OnPrevious()\r
177                 {\r
178                         val = !val;\r
179                 }\r
180 \r
181                 public override string ToString()\r
182                 {\r
183                         CResources cr = CDTXMania.Instance.Resources;\r
184                         return val ? cr.Label("strCfgOn") : cr.Label("strCfgOff");\r
185                 }\r
186 \r
187                 public void Initialize(string lbl, string expl)\r
188                 {\r
189                         label = lbl;\r
190                         explanation = expl;\r
191                         strname = null;\r
192                 }\r
193 \r
194                 public void Initialize( string strname_ )\r
195                 {\r
196                         label = null;\r
197                         explanation = null;\r
198                         strname = strname_;\r
199                 }\r
200         }\r
201 \r
202         [DataContract]\r
203         public class COptionInteger : COption<int>\r
204         {\r
205                 public int nStep;\r
206                 private int nMin;\r
207                 private int nMax;\r
208 \r
209                 public static implicit operator int (COptionInteger n)\r
210                 {\r
211                         return n.Value;\r
212                 }\r
213 \r
214                 public override int Index\r
215                 {\r
216                         get\r
217                         {\r
218                                 return val;\r
219                         }\r
220                 }\r
221 \r
222                 public COptionInteger(int init)\r
223                 {\r
224                         nMin = int.MinValue;\r
225                         nMax = int.MaxValue;\r
226                         val = init;\r
227                 }\r
228 \r
229                 public override int Value\r
230                 {\r
231                         get\r
232                         {\r
233                                 return base.Value;\r
234                         }\r
235 \r
236                         set\r
237                         {\r
238                                 base.Value = value;\r
239                                 LimitValue();\r
240                         }\r
241                 }\r
242 \r
243                 private void LimitValue()\r
244                 {\r
245                         if (val >= nMax)\r
246                         {\r
247                                 val = nMax - 1;\r
248                         }\r
249                         if (val < nMin)\r
250                         {\r
251                                 val = nMin;\r
252                         }\r
253                 }\r
254 \r
255                 public override void OnNext()\r
256                 {\r
257                         IInputDevice keyboard = CDTXMania.Instance.Input管理.Keyboard;\r
258                         if ( keyboard.bキーが押されている( (int) SharpDX.DirectInput.Key.LeftControl ) || keyboard.bキーが押されている( (int) SharpDX.DirectInput.Key.RightControl ) )\r
259                         {\r
260                                 val+=nStep;\r
261                         }\r
262                         else\r
263                         {\r
264                                 val++;\r
265                         }\r
266                         LimitValue();\r
267                 }\r
268 \r
269                 public override void OnPrevious()\r
270                 {\r
271                         IInputDevice keyboard = CDTXMania.Instance.Input管理.Keyboard;\r
272                         if ( keyboard.bキーが押されている( (int) SharpDX.DirectInput.Key.LeftControl ) || keyboard.bキーが押されている( (int) SharpDX.DirectInput.Key.RightControl ) )\r
273                         {\r
274                                 val-=nStep;\r
275                         }\r
276                         else\r
277                         {\r
278                                 val--;\r
279                         }\r
280                         LimitValue();\r
281                 }\r
282 \r
283                 public Converter<int, string> ValueFormatter;\r
284 \r
285                 public override string ToString()\r
286                 {\r
287                         string ret = "";\r
288                         if (ValueFormatter != null)\r
289                         {\r
290                                 ret = ValueFormatter(val);\r
291                         }\r
292                         else\r
293                         {\r
294                                 ret = val.ToString();\r
295                         }\r
296                         return ret;\r
297                 }\r
298 \r
299                 public void Initialize(string lbl, string expl, int min = int.MinValue, int max = int.MaxValue, int step = 1)\r
300                 {\r
301                         label = lbl;\r
302                         explanation = expl;\r
303                         nMin = min;\r
304                         nMax = max;\r
305                         nStep = step;\r
306                         strname = null;\r
307                 }\r
308                 public void Initialize( string _strname, int min = int.MinValue, int max = int.MaxValue, int step = 1 )\r
309                 {\r
310                         label = null;\r
311                         explanation = null;\r
312                         nMin = min;\r
313                         nMax = max;\r
314                         nStep = step;\r
315                         strname = _strname;\r
316                 }\r
317         }\r
318 \r
319         public interface IOptionList\r
320         {\r
321 \r
322         }\r
323 \r
324         [DataContract]\r
325         public abstract class COptionList<T> : COption<T>, IOptionList\r
326         {\r
327                 protected T[] vals;\r
328                 protected int ptr;\r
329                 public int Length { get; protected set; }\r
330 \r
331                 public T this[int idx]\r
332                 {\r
333                         get\r
334                         {\r
335                                 return vals[idx];\r
336                         }\r
337                 }\r
338 \r
339                 public override T Value\r
340                 {\r
341                         get\r
342                         {\r
343                                 return base.Value;\r
344                         }\r
345 \r
346                         set\r
347                         {\r
348                                 base.Value = value;\r
349                                 for (int i = 0; i < Length; ++i)\r
350                                 {\r
351                                         if (vals[i].Equals(value))\r
352                                         {\r
353                                                 ptr = i;\r
354                                         }\r
355                                 }\r
356                         }\r
357                 }\r
358 \r
359                 public override int Index\r
360                 {\r
361                         get\r
362                         {\r
363                                 return ptr;\r
364                         }\r
365                         set\r
366                         {\r
367                                 ptr = value;\r
368                                 if (ptr >= Length) ptr = Length - 1;\r
369                                 if (ptr < 0) ptr = 0;\r
370                                 val = vals[ptr];\r
371                         }\r
372                 }\r
373 \r
374                 public override void OnNext()\r
375                 {\r
376                         ++ptr;\r
377                         if (ptr >= Length)\r
378                         {\r
379                                 ptr = 0;\r
380                         }\r
381                         val = vals[ptr];\r
382                 }\r
383 \r
384                 public override void OnPrevious()\r
385                 {\r
386                         --ptr;\r
387                         if (ptr < 0)\r
388                         {\r
389                                 ptr = Length - 1;\r
390                         }\r
391                         val = vals[ptr];\r
392                 }\r
393 \r
394                 public override string ToString()\r
395                 {\r
396                         return val.ToString();\r
397                 }\r
398 \r
399         }\r
400 \r
401 \r
402         /// <summary>\r
403         /// 列挙定数用オプションアイテム。\r
404         /// </summary>\r
405         /// <typeparam name="E">\r
406         /// 列挙型。ただし、列挙型以外を渡してもコンパイル時エラーとならないので注意してください。(where 制約不可)\r
407         /// また E のメンバに負の値を持つメンバを入れると意図した順番になりません。</typeparam>\r
408         [DataContract]\r
409         public class COptionEnum<E> : COptionList<E> where E : struct\r
410         {\r
411                 public static implicit operator E(COptionEnum<E> e)\r
412                 {\r
413                         return e.Value;\r
414                 }\r
415 \r
416                 /// <summary>\r
417                 /// リフレクションから列挙定数の集合を取得し、内部ポインタでまわします。\r
418                 /// ※実行時型情報の扱いは基本的に重いので注意してください。\r
419                 /// </summary>\r
420                 public COptionEnum(E init)\r
421                 {\r
422                         val = init;\r
423                 }\r
424 \r
425                 public void Initialize(string lbl, string expl, Type type)\r
426                 {\r
427                         label = lbl;\r
428                         explanation = expl;\r
429                         strname = null;\r
430                         InitialieMain( type );\r
431                 }\r
432                 public void Initialize( string _strname, Type type )\r
433                 {\r
434                         label = null;\r
435                         explanation = null;\r
436                         strname = _strname;\r
437                         InitialieMain( type );\r
438                 }\r
439                 private void InitialieMain( Type type )\r
440                 {\r
441                         Length = type.GetEnumValues().Length;\r
442                         vals = new E[Length];\r
443                         int initptr = -1;\r
444                         ptr = 0;\r
445                         foreach (E t in typeof(E).GetEnumValues())\r
446                         {\r
447                                 if (t.Equals(val))\r
448                                 {\r
449                                         initptr = ptr;\r
450                                 }\r
451                                 vals[ptr] = t;\r
452                                 ++ptr;\r
453                         }\r
454                         if (initptr == -1)\r
455                         {\r
456                                 val = vals[0];\r
457                                 ptr = 0;\r
458                         }\r
459                         else\r
460                         {\r
461                                 ptr = initptr;\r
462                         }\r
463                 }\r
464 \r
465         }\r
466 \r
467         [DataContract]\r
468         public class COptionString : COption<string>\r
469         {\r
470                 public static implicit operator string (COptionString s)\r
471                 {\r
472                         return s.Value;\r
473                 }\r
474 \r
475                 public COptionString(string init)\r
476                 {\r
477                         val = init;\r
478                 }\r
479 \r
480                 public void Initialize(string lbl, string expl)\r
481                 {\r
482                         label = lbl;\r
483                         explanation = expl;\r
484                         strname = null;\r
485                 }\r
486                 public void Initialize( string _strname )\r
487                 {\r
488                         label = null;\r
489                         explanation = null;\r
490                         strname = _strname;\r
491                 }\r
492 \r
493                 public override string ToString()\r
494                 {\r
495                         return val;\r
496                 }\r
497         }\r
498 \r
499         [DataContract]\r
500         public class COptionStringList : COptionList<string>\r
501         {\r
502                 public COptionStringList(string init)\r
503                 {\r
504                         val = init;\r
505                 }\r
506 \r
507                 public void Initialize(string lbl, string expl, string[] initvals)\r
508                 {\r
509                         label = lbl;\r
510                         explanation = expl;\r
511                         strname = null;\r
512                         InitializeMain( initvals );\r
513                 }\r
514                 public void Initialize( string _strname, string[] initvals )\r
515                 {\r
516                         label = null;\r
517                         explanation = null;\r
518                         strname = _strname;\r
519                         InitializeMain( initvals );\r
520                 }\r
521                 public void InitializeMain( string[] initvals )\r
522                 {\r
523                         Length = initvals.Length;\r
524                         vals = new string[Length];\r
525                         int initptr = -1;\r
526                         ptr = 0;\r
527                         foreach (var t in initvals)\r
528                         {\r
529                                 if (t == val)\r
530                                 {\r
531                                         initptr = ptr;\r
532                                 }\r
533                                 vals[ptr] = t;\r
534                                 ++ptr;\r
535                         }\r
536 \r
537                         if (initptr == -1)\r
538                         {\r
539                                 val = vals[0];\r
540                                 ptr = 0;\r
541                         }\r
542                         else\r
543                         {\r
544                                 ptr = initptr;\r
545                         }\r
546                 }\r
547         }\r
548 \r
549         [DataContract]\r
550         public class COptionFloat : COption<float>\r
551         {\r
552                 public static implicit operator float (COptionFloat f)\r
553                 {\r
554                         return f.Value;\r
555                 }\r
556 \r
557                 public COptionFloat(float init)\r
558                 {\r
559                         val = init;\r
560                 }\r
561 \r
562                 public void Initialize( string lbl, string expl )\r
563                 {\r
564                         label = lbl;\r
565                         explanation = expl;\r
566                         strname = null;\r
567                 }\r
568                 public void Initialize( string _strname )\r
569                 {\r
570                         label = null;\r
571                         explanation = null;\r
572                         strname = _strname;\r
573                 }\r
574 \r
575                 public override string ToString()\r
576                 {\r
577                         return val.ToString();\r
578                 }\r
579         }\r
580 \r
581         public class COptionLabel : COptionString\r
582         {\r
583                 public COptionLabel(string lbl, string expl)\r
584                         : base("")\r
585                 {\r
586                         type = EOptionType.Other;\r
587                         label = lbl;\r
588                         explanation = expl;\r
589                         strname = null;\r
590                 }\r
591                 public COptionLabel( string _strname )\r
592                         : base( "" )\r
593                 {\r
594                         type = EOptionType.Other;\r
595                         label = null;\r
596                         explanation = null;\r
597                         strname = _strname;\r
598                 }\r
599         }\r
600 \r
601         [DataContract]\r
602         public class COptionDictionary<K, V> : COption<Dictionary<K, V>>\r
603         {\r
604                 public V this[K t]\r
605                 {\r
606                         get\r
607                         {\r
608                                 return Value[t];\r
609                         }\r
610                 }\r
611         }\r
612 \r
613         [DataContract]\r
614         public class COptionKeyAssign : COption<CKeyAssign>\r
615         {\r
616                 public EInputDevice 入力デバイス\r
617                 {\r
618                         get\r
619                         {\r
620                                 return Value.InputDevice;\r
621                         }\r
622                         set\r
623                         {\r
624                                 Value.InputDevice = value;\r
625                         }\r
626                 }\r
627 \r
628                 public int ID\r
629                 {\r
630                         get\r
631                         {\r
632                                 return Value.ID;\r
633                         }\r
634                         set\r
635                         {\r
636                                 Value.ID = value;\r
637                         }\r
638                 }\r
639 \r
640                 public int コード\r
641                 {\r
642                         get\r
643                         {\r
644                                 return Value.Code;\r
645                         }\r
646                         set\r
647                         {\r
648                                 Value.Code = value;\r
649                         }\r
650                 }\r
651 \r
652                 public COptionKeyAssign()\r
653                 {\r
654                         val = new CKeyAssign(EInputDevice.Unknown, 0, 0);\r
655                 }\r
656 \r
657                 public void Reset()\r
658                 {\r
659                         Value.InputDevice = EInputDevice.Unknown;\r
660                         Value.ID = 0;\r
661                         Value.Code = 0;\r
662                 }\r
663 \r
664                 public void CopyFrom(CKeyAssign t)\r
665                 {\r
666                         Value.InputDevice = t.InputDevice;\r
667                         Value.ID = t.ID;\r
668                         Value.Code = t.Code;\r
669                 }\r
670         }\r
671 \r
672         [DataContract]\r
673         public class COptionPadBool : STPadValue<COptionBool>\r
674         {\r
675                 private bool DetermineAssignValue(EThreeState state)\r
676                 {\r
677                         return state == EThreeState.On ? true : state == EThreeState.Off ? false : false;\r
678                 }\r
679 \r
680                 public bool bIsAutoHH\r
681                 {\r
682                         get\r
683                         {\r
684                                 return !LC && HH && !SD && !BD && !HT && !LT && !FT && !CY && !RD && HHO;\r
685                         }\r
686                 }\r
687 \r
688                 public bool bIsAutoBD\r
689                 {\r
690                         get\r
691                         {\r
692                                 return !LC && !HH && !SD && BD && !HT && !LT && !FT && !CY && !RD && !HHO;\r
693                         }\r
694                 }\r
695 \r
696                 public bool bIsAutoNeck(EPart e)\r
697                 {\r
698                         bool ret = false;\r
699                         if (e == EPart.Guitar)\r
700                         {\r
701                                 ret = GtR && GtG && GtB && !GtPick;\r
702                         }\r
703                         else if (e == EPart.Bass)\r
704                         {\r
705                                 ret = BsR && BsG && BsB && !BsPick;\r
706                         }\r
707                         return ret;\r
708                 }\r
709 \r
710                 public bool bIsAutoPick(EPart e)\r
711                 {\r
712                         bool ret = false;\r
713                         if (e == EPart.Guitar)\r
714                         {\r
715                                 ret = !GtR && !GtG && !GtB && GtPick;\r
716                         }\r
717                         else if (e == EPart.Bass)\r
718                         {\r
719                                 ret = !BsR && !BsG && !BsB && BsPick;\r
720                         }\r
721                         return ret;\r
722                 }\r
723 \r
724                 public void SetAutoHH()\r
725                 {\r
726                         Set(EPart.Drums, EThreeState.Off);\r
727                         HH.Value = true;\r
728                 }\r
729 \r
730                 public void SetAutoBD()\r
731                 {\r
732                         Set(EPart.Drums, EThreeState.Off);\r
733                         BD.Value = true;\r
734                 }\r
735 \r
736                 public void SetAutoPick(EPart e)\r
737                 {\r
738                         Set(e, EThreeState.Off);\r
739                         if (e == EPart.Drums)\r
740                         {\r
741                                 GtPick.Value = true;\r
742                         }\r
743                         else if (e == EPart.Bass)\r
744                         {\r
745                                 BsPick.Value = true;\r
746                         }\r
747                 }\r
748 \r
749                 public void SetAutoNeck(EPart e)\r
750                 {\r
751                         Set(e, EThreeState.Off);\r
752                         if (e == EPart.Drums)\r
753                         {\r
754                                 GtR.Value = true;\r
755                                 GtG.Value = true;\r
756                                 GtB.Value = true;\r
757                         }\r
758                         else if (e == EPart.Bass)\r
759                         {\r
760                                 BsR.Value = true;\r
761                                 BsG.Value = true;\r
762                                 BsB.Value = true;\r
763                         }\r
764                 }\r
765 \r
766                 public void Set(EPart e, EThreeState state)\r
767                 {\r
768                         bool val = DetermineAssignValue(state);\r
769                         if (EThreeState.X != state)\r
770                         {\r
771                                 if (e == EPart.Drums)\r
772                                 {\r
773                                         LC.Value = HH.Value = HHO.Value = SD.Value =\r
774                                                         BD.Value = HT.Value = LT.Value = FT.Value = CY.Value = RD.Value = val;\r
775                                 }\r
776                                 else if (e == EPart.Guitar)\r
777                                 {\r
778                                         GtR.Value = GtG.Value = GtB.Value = GtPick.Value = GtWail.Value = val;\r
779                                 }\r
780                                 else if (e == EPart.Bass)\r
781                                 {\r
782                                         BsR.Value = BsG.Value = BsB.Value = BsPick.Value = BsWail.Value = val;\r
783                                 }\r
784                         }\r
785                 }\r
786 \r
787                 public bool IsAllFalse(EPart x)\r
788                 {\r
789                         bool ret = false;\r
790                         if (x == EPart.Guitar)\r
791                         {\r
792                                 ret = !GtR && !GtG && !GtB && !GtPick && !GtWail;\r
793                         }\r
794                         else if (x == EPart.Bass)\r
795                         {\r
796                                 ret = !BsR && !BsG && !BsB && !BsPick && !BsWail;\r
797                         }\r
798                         else if (x == EPart.Drums)\r
799                         {\r
800                                 ret = !LC && !HH && !SD && !BD && !HT && !LT && !FT && !CY && !RD && !HHO;\r
801                         }\r
802                         return ret;\r
803                 }\r
804 \r
805                 public bool IsAllTrue(EPart x)\r
806                 {\r
807                         bool ret = false;\r
808                         if (x == EPart.Guitar)\r
809                         {\r
810                                 ret = GtR && GtG && GtB && GtPick && GtWail;\r
811                         }\r
812                         else if (x == EPart.Bass)\r
813                         {\r
814                                 ret = BsR && BsG && BsB && BsPick && BsWail;\r
815                         }\r
816                         else if (x == EPart.Drums)\r
817                         {\r
818                                 ret = LC && HH && SD && BD && HT && LT && FT && CY && RD && HHO;\r
819                         }\r
820                         return ret;\r
821                 }\r
822         }\r
823 \r
824 }\r