MQLで書かれたUIのギャラリー - ページ 69

 

パラメータ境界の時差保護とユーザー警告の実装に関するトピックを続ける前に、それに直接先行するもう一つのトピックについて触れておく。すなわち、パラメータのプリセット である。

ほとんどのMQLプログラムには入力 カテゴリの変数があります。これらはグローバル・レベルで宣言され、1つの設定ウィンドウで見ることができます。このウィンドウはプログラムの開始時に表示され、その中でユーザーは「外部」変数の初期値を変更することができます。しかしその前に、ユーザーはプログラム内部で外部変数を初期化します。重要なのは、プログラムのプリセットは万能ではないということであり、そのために、起動のたびに設定する可能性を必要とする変数のカテゴリーが存在するのである。また、プログラム実行中に手動で外部変数にアクセスすることは不可能であり、再起動が必要であることも知られている。グラフィカル・インターフェースでは、この必要性がなくなります。プログラム設定は実行時に開くことができます。

しかし、開始時にプログラム・パラメーターに初期値を設定する必要性は変わらない

グラフィカル・インターフェースの場合 標準設定ウィンドウが不要になるため、入力 タイプの変数を宣言する意味がなくなりますが、本質は変わりません。 入力 変数の代わりに、コントロールのパラメータに初期値を設定する必要があります

プログラムの初期化では、標準ウィンドウではなく、独自のウィンドウに 初期値を設定する関数を呼び出す必要があります。 オプションとして、V_CURRENT 値やON/OFF 状態などを設定するインターフェイス構築の段階で、KIB-constructorでこれを行うこともできますが、現在はプログラムで要素を初期化することが可能です。これにより、コンストラクタ内での要素の初期化とプログラム内での要素の初期化を組み合わせることが可能になりました。

そのため、OnInit() から呼び出される特別な関数が必要になります。

この関数は具体的に何をするのか:

  • プログラム開始時に必要なウィンドウを開く。
  • ターゲット・コントロールに値を設定する。

この関数は何と呼ばれるのでしょうか?

私はこれをInitialize() と呼ぶことにするが、誰でも独自の変種を思いつくことができる。

重要な のは、この関数はどのインターフェイスのExpert Advisorにもなければ ならないということです。Expert Advisorの OnTick() 関数やインジケーターのOnCalculate() 関数と比較することができます。これを理解することが重要です


関数はどのような値を返しますか?

関数はvoid 型です 値を返す必要はありません。呼び出されると、必要なウィンドウを開き、項目のパラメータを初期化し、場合によってはいくつかのプロパティをプリセットします。基本的にはそれだけだ。理論的には、この中でパラメータの初期値を設定することもできるが、値の制御はAPIファイルやタイマーからのエレメント・イベント時に呼び出される別の関数で実装することになると思う。次のバージョンでは、コントロール・コールのプリントアウトを書くことになるだろう。

*現時点では、Expert Advisorsのインターフェイスのコンセプトは形成されたばかりであり、多くの発見があることを考慮する ことが重要です。


以下は、現在のデモ・プロジェクトにおける Expert Advisor のインターフェース初期化関数の例である:

1.関数の呼び出し

//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int _OnInit()
  {
   //------------------------------------------------
   //Initializing program interface:
   //------------------------------------------------
   Initialize();
   //------------------------------------------------


2.関数の実装

void Initialize()   
{
   //------------------------------------------------
   //Opening the windows:
   //------------------------------------------------
   //1. "Main Parameters". 

    w_14_Main_Parameters();
   //------------------------------------------------

   //------------------------------------------------
   //2. "Input parameters".

   w_10_Input_parameters();
   //------------------------------------------------

   //------------------------------------------------
   //3. "Setting example 1"

   w_6_Settings_example_1();
   //------------------------------------------------


  //------------------------------------------------
  //Initializing the elements:
  //------------------------------------------------
  
   w6_d_p5_S_EDIT_Spin_the_value(55);

   w6_i_p3_H_SLIDER_Roll_the_value(55);

   w14_i_p3_V_SLIDER_Vertical_slider(55);

   w14_s_p4_EDIT_Max("100");

   w14_s_p4_EDIT_Min("0");

   w14_s_p4_EDIT_Selected("55");

   w15_i_p2_P_BAR_P1(55);

   w15_s_p4_VALUE_V1("55");
  //------------------------------------------------
}


今のところ、関数の構造は次のようになっている。非常に単純な関数。ウィンドウを開き、要素のパラメータに必要な値を送る。ウィンドウを開くと、再描画を追加することなく要素の必要な値が即座に表示されるので、要素の初期化とウィンドウの開き方をところどころ変更することは可能である。しかし、これらは些細なことです。


それでは、本題であるパラメータの段階的保護の実装に 移りましょう

 

14.パラメータ境界の段階的保護の実現:

  • 1.プリセット境界内の設定を制御し、警告システムを作成するためのロジックを記述する。
  • 2. 2.最初の警告: ユーザーは、設定を担当する要素の一部の色を変更する形で信号を受け取ります。 (テキスト、ベース、フレーム、スライダー バーの色を値の 境界に リンクさ せる)。
  • 3.2回目の警告:ダイアログボックスを開き、リスク通知と元の設定に戻すことを提案する。(キャンセル」 ボタンをクリックしたときに、前の設定に戻ることが実際に可能かどうかテストしてみましょう)。
  • 4. 第三の 警告: これ以上の設定変更をブロックし、ユーザーの手動確認を要求する警告ウィンドウを開く。(警告ウィンドウが表示されたときのウィンドウと要素のブロックについて確認しましょう)。

//------------------------------------------------------------------------------------------------------------

プリセットされた範囲内で設定を制御するロジックを記述し、警告システムを作成する:

  • 実装の最初の部分は、選択された要素のパラメータの初期値を設定し、必要なウィンドウを開くことです。そのために、Initialise() 関数を記述し、その呼び出しを_OnInit()関数内に記述します。
  • APIファイルを開き、要素の接続を記述します コモンチェインの各要素の場合、呼び出しを記述し、他のターゲット要素に値を渡します。例えば、ボタンがあるフィールドのイベントで、水平スライダーを呼び出し、値を渡します。そして、イベントがスライダーのケースに来たら、それをボタン付きフィールドに戻し、さらに垂直スライダーにも渡します。後者は順番に、それ自身の近くの入力フィールドとプログレス・バー・ウィンドウに値を渡す。全部で、いくつかの方向に値を渡すチェーンには、7つの主要な要素があります。それがこちらです:設定例1"の"Spin the value"と"Roll the value"、"Main parameters"の"V_SLIDER"、"Selected"と"Percent"、"Processing the data... "" VALUE " と " P_BAR" です。
  • パート3: 接続をテストする。
  • 第四部: 条件付きパラメタ・コントロール関数を書きましょう:void Risk_management_group_1()。この関数のタスクは、要素のグループ内で 危険な値の境界に近づいたことをユーザーに知らせ、許容限度を超えたときに警告することです。この関数は、関連する要素から値を受け取り、条件内部で設定されたフィルターに通します。適切なリスクレベルのテキストとフレームの色の変更によって警告を実装し、チェーンのすべての要素に送信します。並行して、追加の確認なしにユーザーがアクションを続行できないようにするブロッキングウィンドウを呼び出します。
  • 第5部: 関数の動作をテストしてみましょう。

//-----------------------------------------------------------------------------

進めましょう:

1.選択された要素のパラメータの初期値を設定し、必要なウィンドウを開きます。そのために、Initialise() 関数を作成 し、 _OnInit() 関数内で呼び出します。

//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int _OnInit()
  {
   //------------------------------------------------
   //Initializing program interface:
   //------------------------------------------------
   Initialize();
   //------------------------------------------------
void Initialize()   
{
   //------------------------------------------------
   //Opening the windows:
   //------------------------------------------------
   //1. "Main Parameters". 
    w_14_Main_Parameters();

   //2. "Input parameters".
   w_10_Input_parameters();

   //3. "Setting example 1"
   w_6_Settings_example_1();

   //------------------------------------------------
  //Initializing the elements:
  //------------------------------------------------
   w6_d_p5_S_EDIT_Spin_the_value(55);
   w6_i_p3_H_SLIDER_Roll_the_value(55);
   w14_i_p3_V_SLIDER_Vertical_slider(55);
   w14_s_p4_EDIT_Max("100");
   w14_s_p4_EDIT_Min("0");
   w14_s_p4_EDIT_Selected("55");
   w15_i_p2_P_BAR_P1(55);
   w15_s_p4_VALUE_V1("55");
  //------------------------------------------------
}

結果:必要なウィンドウが開き、対象の要素に 初期値が設定さ れる。


2.APIファイルを開き、エレメントの接続を記述 します。各エレメントの 場合 、呼び出しを記述し、チェーン内の他のターゲット・エレメントに値を渡します:

case Settings_example_1___Spin_the_value:
  
               //------------------------------------------------------------------------------------------------------
               //What to do when the value is set?
               //------------------------------------------------------------------------------------------------------
               //Min value:  NOT SET  |   Max value:  NOT SET  |   V_step:  1.7  |   Default value:  468.99  |  Digits: 3
               //------------------------------------------------------------------------------------------------------
               w6_i_p3_H_SLIDER_Roll_the_value((int)value);

               //------------------------------------------------------------------------------------------------------
               //Your comment:
               //------------------------------------------------------------------------------------------------------
               break;
case Settings_example_1___Roll_the_value:
  
               //------------------------------------------------------------------------------------------------------
               //What to do when the slider's handle is moved?
               //------------------------------------------------------------------------------------------------------
               //Min value:  0  |   Max value:  100  |   V_step:  1  |   Default value:  55  |  Digits: Integer value
               //------------------------------------------------------------------------------------------------------
               //Transferring the value:
               w14_i_p3_V_SLIDER_Vertical_slider((int)value);

               w6_d_p5_S_EDIT_Spin_the_value((double)value);
               //------------------------------------------------------------------------------------------------------
               //Your comment:
               //------------------------------------------------------------------------------------------------------
               break;
case Main_Parameters___Vertical_slider:
  
               //------------------------------------------------------------------------------------------------------
               //What to do when the slider's handle is moved?
               //------------------------------------------------------------------------------------------------------
               //Min value:  0  |   Max value:  100  |   V_step:  1  |   Default value:  50  |  Digits: Integer value
               //------------------------------------------------------------------------------------------------------
               {
                //----------------------------------------------------- 
                //Transferring value to other destinations:
                //----------------------------------------------------- 
                w14_s_p4_EDIT_Percent(value);
                //-----------------------------------------------------
                w14_s_p4_EDIT_Selected(value);
                //-----------------------------------------------------
                w15_i_p2_P_BAR_P1((int)value);
                //-----------------------------------------------------
                w15_s_p4_VALUE_V1(value);
                //-----------------------------------------------------
                w6_i_p3_H_SLIDER_Roll_the_value((int)value);
                //-----------------------------------------------------
                w6_d_p5_S_EDIT_Spin_the_value((double)value);
                //-----------------------------------------------------
                w8_s_p4_CELL_Account_balance__Value(value);
                //------------------------------------------------------------------------------------------------------
                //Your comment:
                //------------------------------------------------------------------------------------------------------
               }
               break;


3.接続をテストする:

結果:要素の値は意図したとおりに接続されている



4.要素グループのパラメータを制御する関数を記述する:void Risk_management_group_1().

void Risk_management_group_1(string value)
{
 uint Color = 0;
 //--------------------
 static uint This_color;
 static bool User_warned, Last_warning;
 //------------------------------------------------------------
 //Setting limit colors:
 //------------------------------------------------------------
 if((int)value < 25)                      Color = clrLightGreen;
 //------------------------------------------------------------
 if((int)value >= 25 && (int)value < 50)  Color = clrLimeGreen;
 //------------------------------------------------------------
 if((int)value >= 50 && (int)value < 70)  Color = clrGreen;
 //------------------------------------------------------------
 if((int)value >= 70 && (int)value < 85)  Color = clrDarkGreen;
 //------------------------------------------------------------
 if((int)value >= 85 && (int)value < 90)  Color = clrBrown;
 //------------------------------------------------------------
 if((int)value >= 90 && (int)value < 95)  Color = C'170,0,0';
 //------------------------------------------------------------
 if((int)value >= 95 && (int)value <=100) Color = clrRed;
 //------------------------------------------------------------  

 //------------------------------------------------------------ 
 //Changing colors when the limits are passed:
 //------------------------------------------------------------
 if(This_color != Color)
   {
    w14_s_p4_EDIT_Percent((string)Color, p4_COLOR_base); 
    //-----------------------------------------------------
    w14_s_p4_EDIT_Selected((string)Color, p4_COLOR_base); 
    //-----------------------------------------------------
    w15_i_p2_P_BAR_P1(Color, p2_COLOR_bar);
    w15_i_p2_P_BAR_P1(Color, p2_COLOR_frame);
    w15_s_p4_VALUE_V1((string)Color, p4_COLOR_frame);
                   
    w8_s_p4_CELL_Account_balance__Value((string)Color, p4_COLOR_text);
    w8_s_p4_CELL_Account_balance__Value((string)Color, p4_COLOR_frame);
    //-----------------------------------------------------
    w14_i_p3_V_SLIDER_Vertical_slider(Color,p3_COLOR_bar);
    //-----------------------------------------------------
    w15_s_p4_VALUE_V1((string)Color, p4_COLOR_text);
    //-----------------------------------------------------
    w6_i_p3_H_SLIDER_Roll_the_value(Color,p3_COLOR_bar);
    //-----------------------------------------------------
    w6_d_p5_S_EDIT_Spin_the_value((double)Color, p5_COLOR_text);
    //-----------------------------------------------------
    w6_d_p5_S_EDIT_Spin_the_value((double)Color, p5_COLOR_frame);
    //-----------------------------------------------------
    w14_i_p1_BUTTON_BUY_OFF(Color, p1_N_COLOR_frame);
    w14_i_p1_BUTTON_BUY_OFF(Color, p1_A_COLOR_frame);
    //-----------------------------------------------------
    w14_i_p1_BUTTON_SELL_OFF(Color, p1_N_COLOR_frame);
    w14_i_p1_BUTTON_SELL_OFF(Color, p1_A_COLOR_frame);
    //-----------------------------------------------------
    w7_s_p4_EDIT_Comment_1(Color, p4_COLOR_frame);
    //-----------------------------------------------------
    This_color = Color;
    //-----------------------------------------------------
   }   
 //-----------------------------------------------------
 //Opening warning window 1:
 //-----------------------------------------------------
 if((int)value >= 85 && (int)value < 95 && !User_warned)
   { 
    //---------------------------------
    //Opening dialog window:
    //---------------------------------
    w_13_Risky_managment(); 
    //---------------------------------
    //Setting flag of warning 1:
    //---------------------------------
    User_warned = true;
    //---------------------------------
   }
 //-----------------------------------------------------
 if((int)value < 85)User_warned = false;
 //-----------------------------------------------------
 //Opening warning window 2:
 //-----------------------------------------------------
 if((int)value >= 96 && !Last_warning)
   { 
    //---------------------------------
    //Calling blocking window:
    //---------------------------------
    w_17_Last_warning();
    //---------------------------------
    //Setting flag of warning 2:
    //---------------------------------
    Last_warning = true;
    //---------------------------------
   }
 //-----------------------------------------------------
 if((int)value < 95)Last_warning = false;                
 //-----------------------------------------------------                 
}

Risk_management_group_1()関数を_OnInit()関数から呼び出す:

//+------------------------------------------------------------------+
//| Expert initialization function                                   |
//+------------------------------------------------------------------+
int _OnInit()
  {
   //------------------------------------------------
   //Initializing program interface:
   //------------------------------------------------
   Initialize();
   //----------------------------------------------------------
   //Checking default value of the parameters in the group:  
   //----------------------------------------------------------
   Risk_management_group_1();
   //----------------------------------------------------------
 

結果意図したとおりに動作するが、入力フィールドに値を入力する際、警告ウィンドウが表示されても入力された値がリセットされない(要改善)。

(*また フレームの色の設定はアップデートで追加されましたが、現在のバージョンにはありません)。


 

次の課題は、入力したパラメーターを「キャンセル」ボタンでキャンセルすることを考えることだ。

これは非常に難しい課題だが、すでに部分的に実装 した。以前の機能を復元してみるつもりだ。

 
色表示に加え、フレーム、テキスト、ベースの点滅を実装しているところだ。明日には完成すると思う。次に、キャンセルボタンによる入力値のキャンセルだ。

問題なのは、エレメントに値を入力すると、即座にカーネルがそれを受け取ってAPIファイルに渡してしまうため、論理的にカスタムコードの処理が発生してしまうことだ。確認ボタンのあるウィンドウで値を受け取るのを、パラメータに到着する前に遅らせ、"Ok "または "Confirm"(または "Apply")をクリックすることにリンクさせる必要がある。

しかしまた、ユーザーがキャンセルボタン(Cancel)をクリックした場合、変更前の値を要素に戻す必要があります。

これは非常に興味深い問題であり、その解決はインターフェースの実用的な有用性を即座に新しいレベルに引き上げる。幸いなことに、ほとんどの場合、この目標はとっくの昔に達成されている。4年前にすでに多くの興味深いことが実装されていたことにただ驚くばかりだ。

週間以内にこの課題を達成し、さらに、テーブルについて真剣に取り組んでみようと思う。
 

前回の内訳では、リスクのカラー表示を適用し、設定したパラメーターの限界値を超えたときにブロックウィンドウを開く方法を紹介した。しかし、予想外の2つの問題が発覚した。

1.リスク管理機能は危険なレベルを越えると最初の警告ウィンドウを開きますが、この瞬間にカーソルを要素上で押したままにしておくと、値が伸び続けて次の条件レベルに達してしまいます。- クリティカルである。

2.クリティカルな値を超えると、最後の警告ウィンドウが開きますが、ユーザーがマウスの左ボタンを押し続けても、値の変化も止められません。

3.ユーザーがマウスボタンを離し、警告ウィンドウを閉じようとしても、閉じることができない。正確には、できない。その理由は、2つのブロックウィンドウが互いにブロックし始めるからである。片方のウィンドウが開いているときは簡単に閉じられるが、2つのウィンドウが同時に開いているときは、インターフェイスの他の部分は何も動作しない。プログラムはまだ動くが、昏睡状態に陥る。

下の画像はその様子を示している:

 

その後、設定ウィンドウの相互ロックの問題を修正し、今ではウィンドウ同士が干渉し合うことはない。互いに衝突することなく、一緒にロック機能を実行する。


あとは、マウスの左ボタンが押されていて、その項目がアクティブな状態であっても、警告ウィンドウがパラメータ値の変更を自動的に停止するようにする必要がある。

 
今日は、パラメータ値の色表示(エレメントの点滅)のトピックの続きを掲載する。この作業は思っていたより少し複雑であることが判明したので、作業を遅らせた。結局、その解決策は費やした時間を正当化するものだった。私見ではあるが。
削除済み  
それは理解できるだろう。
 
Jin Rong Xia #:
あなたなら理解できる
はい、わかります。翻訳機はうまく機能している