//--- 説明 #property description "Script draws \"Trend Line\" graphical object." #property description "Anchor point coordinates are set in percentage of" #property description "the chart window size." //--- スクリプトの起動時に入力パラメータのウィンドウを表示する #property script_show_inputs //--- スクリプト入力パラメータ input string InpName="Trend"; // 線の名称 input int InpDate1=35; // 1 番目のポイントの日付( % ) input int InpPrice1=60; // 1 番目のポイントの価格( % ) input int InpDate2=65; // 2 番目のポイントの日付( % ) input int InpPrice2=40; // 2 番目のポイントの価格( % ) input color InpColor=clrRed; // 線の色 input ENUM_LINE_STYLE InpStyle=STYLE_DASH; // 線のスタイル input int InpWidth=2; // 線の幅 input bool InpBack=false; // 背景の線 input bool InpSelection=true; // 強調表示して移動 input bool InpRayLeft=false; // 線の左への継続 input bool InpRayRight=false; // 線の右への継続 input bool InpHidden=true; // オブジェクトリストに隠す input long InpZOrder=0; // マウスクリックの優先順位 //+------------------------------------------------------------------+ //| 与えられた座標で傾向線を作成する | //+------------------------------------------------------------------+ bool TrendCreate(const long chart_ID=0, // チャート識別子 const string name="TrendLine", // 線の名称 const int sub_window=0, // サブウィンドウ番号 datetime time1=0, // 1 番目のポイントの時間 double price1=0, // 1 番目のポイントの価格 datetime time2=0, // 2 番目のポイントの時間 double price2=0, // 2 番目のポイントの価格 const color clr=clrRed, // 線の色 const ENUM_LINE_STYLE style=STYLE_SOLID, // 線のスタイル const int width=1, // 線の幅 const bool back=false, // 背景で表示する const bool selection=true, // 強調表示して移動 const bool ray_left=false, // 線の左への継続 const bool ray_right=false, // 線の右への継続 const bool hidden=true, // オブジェクトリストに隠す const long z_order=0) // マウスクリックの優先順位 { //--- 設定されてない場合アンカーポイントの座標を設定する ChangeTrendEmptyPoints(time1,price1,time2,price2); //--- エラー値をリセットする ResetLastError(); //--- 与えられた座標で傾向線を作成する if(!ObjectCreate(chart_ID,name,OBJ_TREND,sub_window,time1,price1,time2,price2)) { Print(__FUNCTION__, ": failed to create a trend line! Error code = ",GetLastError()); return(false); } //--- 線の色を設定する ObjectSetInteger(chart_ID,name,OBJPROP_COLOR,clr); //--- 線の表示スタイルを設定する ObjectSetInteger(chart_ID,name,OBJPROP_STYLE,style); //--- 線の幅を設定する ObjectSetInteger(chart_ID,name,OBJPROP_WIDTH,width); //--- 前景(false)または背景(true)に表示 ObjectSetInteger(chart_ID,name,OBJPROP_BACK,back); //--- マウスで線を移動させるモードを有効(true)か無効(false)にする //--- ObjectCreate 関数を使用してグラフィックオブジェクトを作成する際、オブジェクトは //--- デフォルトではハイライトされたり動かされたり出来ない。このメソッド内では、選択パラメータは //--- デフォルトでは true でハイライトと移動を可能にする。 ObjectSetInteger(chart_ID,name,OBJPROP_SELECTABLE,selection); ObjectSetInteger(chart_ID,name,OBJPROP_SELECTED,selection); //--- 線の表示を左に延長するモードを有効(true)か無効(false)にする ObjectSetInteger(chart_ID,name,OBJPROP_RAY_LEFT,ray_left); //--- 線の表示を右に延長するモードを有効(true)か無効(false)にする ObjectSetInteger(chart_ID,name,OBJPROP_RAY_RIGHT,ray_right); //--- オブジェクトリストのグラフィックオブジェクトを非表示(true)か表示(false)にする ObjectSetInteger(chart_ID,name,OBJPROP_HIDDEN,hidden); //--- チャートのマウスクリックのイベントを受信するための優先順位を設定する ObjectSetInteger(chart_ID,name,OBJPROP_ZORDER,z_order); //--- 実行成功 return(true); } //+------------------------------------------------------------------+ //| 傾向線のアンカーポイントを移動する | //+------------------------------------------------------------------+ bool TrendPointChange(const long chart_ID=0, // チャート識別子 const string name="TrendLine", // 線の名称 const int point_index=0, // アンカーポイントのインデックス datetime time=0, // アンカーポイントの時間座標 double price=0) // アンカーポイントの価格座標 { //--- ポイントの位置が設定されていない場合、売値を有する現在足に移動する if(!time) time=TimeCurrent(); if(!price) price=SymbolInfoDouble(Symbol(),SYMBOL_BID); //--- エラー値をリセットする ResetLastError(); //--- 傾向線のアンカーポイントを移動する if(!ObjectMove(chart_ID,name,point_index,time,price)) { Print(__FUNCTION__, ": failed to move the anchor point! Error code = ",GetLastError()); return(false); } //--- 実行成功 return(true); } //+------------------------------------------------------------------+ //| この関数はチャートから傾向線を削除する | //+------------------------------------------------------------------+ bool TrendDelete(const long chart_ID=0, // チャート識別子 const string name="TrendLine") // 線の名称 { //--- エラー値をリセットする ResetLastError(); //--- 傾向線を削除する if(!ObjectDelete(chart_ID,name)) { Print(__FUNCTION__, ": failed to delete a trend line! Error code = ",GetLastError()); return(false); } //--- 実行成功 return(true); } //+------------------------------------------------------------------+ //| 傾向線のアンカーポイントの値をチェックして | //| 空の物には初期値を設定する | //+------------------------------------------------------------------+ void ChangeTrendEmptyPoints(datetime &time1,double &price1, datetime &time2,double &price2) { //--- 1 番目のポイントの時間が設定されていない場合、現在足になる if(!time1) time1=TimeCurrent(); //--- 1 番目のポイントの価格が設定されていない場合、売値になる if(!price1) price1=SymbolInfoDouble(Symbol(),SYMBOL_BID); //--- 2 番目のポイントの時間が設定されていない場合、2 番目から 9 バー左に置かれる if(!time2) { //--- 最後の 10 バーのオープン時間を受信するための配列 datetime temp[10]; CopyTime(Symbol(),Period(),time1,10,temp); //--- 2 番目のポイントを最初のものから 9 バー左に設定する time2=temp[0]; } //--- 2 番目のポイントの価格は設定されていない場合は 1 番目のポイントと等しい if(!price2) price2=price1; } //+------------------------------------------------------------------+ //| スクリプトプログラムを開始する関数 | //+------------------------------------------------------------------+ void OnStart() { //--- 入力パラメータの正しさをチェックする if(InpDate1<0 || InpDate1>100 || InpPrice1<0 || InpPrice1>100 || InpDate2<0 || InpDate2>100 || InpPrice2<0 || InpPrice2>100) { Print("Error! Incorrect values of input parameters!"); return; } //--- チャートウィンドウで表示されているバーの数 int bars=(int)ChartGetInteger(0,CHART_VISIBLE_BARS); //--- 価格配列サイズ int accuracy=1000; //--- アンカーポイントの座標の設定と変更に使用される日付と //--- 価格の値を格納するための配列 datetime date[]; double price[]; //--- メモリ割り当て ArrayResize(date,bars); ArrayResize(price,accuracy); //--- 日付配列に書き込む ResetLastError(); if(CopyTime(Symbol(),Period(),0,bars,date)==-1) { Print("Failed to copy time values! Error code = ",GetLastError()); return; } //--- 価格配列に書き込む //--- チャートの最高値と最安値を見つける double max_price=ChartGetDouble(0,CHART_PRICE_MAX); double min_price=ChartGetDouble(0,CHART_PRICE_MIN); //--- 価格の変更ステップを定義し、配列に書き込む double step=(max_price-min_price)/accuracy; for(int i=0;i<accuracy;i++) price[i]=min_price+i*step; //--- 線を描画するポイントを定義する int d1=InpDate1*(bars-1)/100; int d2=InpDate2*(bars-1)/100; int p1=InpPrice1*(accuracy-1)/100; int p2=InpPrice2*(accuracy-1)/100; //--- 傾向線を作成する if(!TrendCreate(0,InpName,0,date[d1],price[p1],date[d2],price[p2],InpColor,InpStyle, InpWidth,InpBack,InpSelection,InpRayLeft,InpRayRight,InpHidden,InpZOrder)) { return; } //--- チャートを再描画して 1 秒待つ ChartRedraw(); Sleep(1000); //--- 線のアンカーポイントを移動する //--- ループカウンタ int v_steps=accuracy/5; //--- 1 番目のアンカーポイントを垂直方向に移動する for(int i=0;i<v_steps;i++) { //--- 次の値を使用する if(p1>1) p1-=1; //--- ポイントを移動する if(!TrendPointChange(0,InpName,0,date[d1],price[p1])) return; //--- スクリプトの動作が強制的に無効にされているかどうかをチェックする if(IsStopped()) return; //--- チャートを再描画する ChartRedraw(); } //--- 2 番目のアンカーポイントを垂直方向に移動する for(int i=0;i<v_steps;i++) { //--- 次の値を使用する if(p2<accuracy-1) p2+=1; //--- ポイントを移動する if(!TrendPointChange(0,InpName,1,date[d2],price[p2])) return; //--- スクリプトの動作が強制的に無効にされているかどうかをチェックする if(IsStopped()) return; //--- チャートを再描画する ChartRedraw(); } //--- 半秒の遅れ Sleep(500); //--- ループカウンタ int h_steps=bars/2; //--- 両方のアンカーポイントを同時に水平方向に移動させる for(int i=0;i<h_steps;i++) { //--- 次の値を使用する if(d1<bars-1) d1+=1; if(d2>1) d2-=1; //--- ポイントをシフトする if(!TrendPointChange(0,InpName,0,date[d1],price[p1])) return; if(!TrendPointChange(0,InpName,1,date[d2],price[p2])) return; //--- スクリプトの動作が強制的に無効にされているかどうかをチェックする if(IsStopped()) return; //--- チャートを再描画する ChartRedraw(); // 0.03 秒の遅れ Sleep(30); } //--- 1 秒の遅れ Sleep(1000); //--- 傾向線を削除する TrendDelete(0,InpName); ChartRedraw(); //--- 1 秒の遅れ Sleep(1000); //--- } |