Metatrader Forum | Forex Expert-Advisor | Broker & Forex Tools

Metatrader Forum | Forex Expert-Advisor | Broker & Forex Tools (http://www.expert-advisor.com/forum/index.php)
-   Programmierung MQL4 (http://www.expert-advisor.com/forum/forumdisplay.php?f=220)
-   -   Trailing Stop in EA einbinden bei vorhandenem SL (http://www.expert-advisor.com/forum/showthread.php?t=6045)

Karabiner 18.03.18 14:52

Trailing Stop in EA einbinden bei vorhandenem SL
 
Hallo Forum,

ich habe mal wieder ein Problem und komme nicht weiter.
Bisher konnte ich mir immer irgendwie selber helfen, aber bei diesem Problem komme ich nicht weiter.

Ich setze über OrderModify den StopLoss und TakeProfit .. nun möchte ich in dem EA auch den TrailingStop implementieren und ich komme einfach nicht hinter das Geheimnis.

Wenn ich die Order modifiziere und den SL setze, wie kann ich dann den SL erneut modifizieren und versetzen. Ich finde immer nur EA´s die den bereits vorhandenen SL aus dem aktiven Trade modifizieren, aber nie einen EA der den SL setzt und je nach Marktinfo versetzt, als Lösungsansatz.

Ich kann also wenig programmieren, nur abkupfern und versuche zu verstehen was andere programmiert haben und es dann einzubauen im EA.

Mein Grund EA ist die Videoanleitung "EA selbst programmieren" .. darauf baut sich alles auf.

a)
Code:

extern double HandelLots = 0.1, SL_prozent = 0.2, TP_prozent = 1.0;
extern int MagicNummer = 12345;
extern int LongOrder, ShortOrder;

Code:

  if (OrderSelect(LongOrder,SELECT_BY_TICKET)==true)
      {
          if(OrderCloseTime() ==0 && OrderStopLoss() ==0 )
          {
         
              StoppLoss= NormalizeDouble (OrderOpenPrice()/(1+(SL_prozent/100)),Digits);
              bool OrderAngepasst = OrderModify (OrderTicket(),OrderOpenPrice(),StoppLoss,OrderTakeProfit(),0,Yellow);
          }
      }




Gruß Karabiner

AVT 18.03.18 22:47

Zitat:

Zitat von Karabiner (Beitrag 40594)
Ich finde immer nur EA´s die den bereits vorhandenen SL aus dem aktiven Trade modifizieren, aber nie einen EA der den SL setzt und je nach Marktinfo versetzt, als Lösungsansatz.

Das ist aus meinen "Erinnerung wie's geht" Schnipseln: 2 Anfangspositionen, 1. Position fester SL + fester TP wird nicht mehr angerührt, 2. Position (um die geht es hier) anfangs genau derselbe SL + fester TP halben Block höher als die 1. Position.
Hat die 2. Position den Punkt erreicht, wo die erste das Ziel erreicht hat, wird zuerst ihr Ziel/TP rausgenommen (also open end), und dann nur noch dem aktuellen Preis mit TrailSL Abstand gefolgt, bis man rausfliegt.
Code:

// zu Anfang berechnete Werte:
// - ProfitMoney ist der Eurowert der 1. TP Position
// - LongBE ist Einstieg+Spread+2*Slippage
// - TrailSL ist der trailing Abstand zum Preis
// voher schon bekannt: es ist eine laufende Long Position
  if(OrderSelect(n,SELECT_BY_POS,MODE_TRADES))    // positions in "Trade"
  {
      //=== break even half range reached:
      //=== half range order: should be closed by TP
      //=== full range order: set order to BE auf Einstand
      if    (  LPosCnt==2 && LEveCnt==0  // not yet even
              && OrderProfit()>ProfitMoney // dist in €
              && Bid>LongBE                // cur above entry
              && OrderStopLoss()<LongBE )  // SL below entry
      {
        if(OrderModify(OrderTicket(),OrderOpenPrice(),
                    LongBE,OrderTakeProfit(),0,Ctrail) )
        {  LEveCnt=1;                // set even counter
            Print(EAname+" LeC="+IntegerToString(LEveCnt,1) );
        }
      }
      //=== trailing: SL was LongBE, TS=block
      //=== take out TP if not yet counted as TPex Takeprofit rausnehmen
      else if(  LPosCnt==2 && LEveCnt==1 && TPxCnt==0
              && Bid>OrderOpenPrice()+(TrailSL) // above cur+block
              && OrderStopLoss()<Bid-TrailSL )  // below cur-block
      {
          if(OrderModify(OrderTicket(),OrderOpenPrice(),
                        LongBE,0,0,Ctrail) )
        {  LEveCnt=1; TPxCnt=1;                // set TP ex counter
            Print(EAname+" TPx="+IntegerToString(TPxCnt,1));
        }
      }
      //=== activate trailing only  nur Trailing
      else if(  LPosCnt==2 && LEveCnt==1 && TPxCnt==1
              && Bid>OrderOpenPrice()+(TrailSL) // above cur+block
              && OrderStopLoss()<Bid-TrailSL )  // below cur-block
      {
        if(OrderModify(OrderTicket(),OrderOpenPrice(),
                        Bid-TrailSL,0,0,Ctrail) )
        {  LEveCnt=1; Print(EAname+" Lmo."); }
      }
  } // == end OrderSelect(n,SELECT_BY_POS,MODE_TRADES)

Ich hoffe, das hilft Dir die Vorgehensweise zu sehen. Bitte nicht einfach abkupfern, die Art nur "if OrderModify ist ok" abzufragen sollte man so nicht einfach machen, sondern besser den Fehlercode holen falls etwas nicht klappt. AVT

Karabiner 19.03.18 17:12

Hallo AVT,

danke erstmal das du auf meien Frage geantwortet hast :).

So ganz hab ich es noch nicht verstanden.

Warum 2 Positionen eröffnen ? Ist das Notwendig damit man den SL nachziehen kann?

Dadurch hat man automatisch auch das doppelte Risiko, wenn der Markt doch anders reagiert, also 2 mal in den SL reinläuft ?!
--------------------------------------------------------------------------------
Erstmal ohne Bezug auf deinen Code Schnipsel

Ich bleib immer an dem zweimaligen OrderModify hängen .. der erste zum setzen des Sl und der zweite zum SL nachziehen .. z.B ist die LongOrder == True setzt er den SL , jetzt muss er aber das erste setzen des SL überspringen und in den SL Trailing reinspringen und das OrderModify "nehmen" ... könnte man da dann mit Hilfe von OrderStopLoss == 0 beim ersten Sl arbeiten? Und für den zweiten Trailing SL OrderStopLoss >0 ?

----------------------------------------------------------------------------------

Also 2 Positionen zum selben Preis .. beide den selben SL .. 1.Position sagen wir TP bei 10€ und 2. Position TP bei 15€ ... wenn jetzt die 1. Position die den TP bei 10€ erreicht hat und dadurch geschlossen wird .. entfernen des TP der 2. Position bei 15€ ... und jetzt arbeitet der Trailing Stop und zieht den SL nach ... aber warum macht er das ? grübel

Gruß
Karabiner

Ps.: ein grundsätzliche Frage .. arbeitet das programm zyklisch von "oben nach unten" ?

AVT 19.03.18 21:52

Zitat:

Zitat von Karabiner (Beitrag 40598)
Warum 2 Positionen eröffnen ? Ist das Notwendig damit man den SL nachziehen kann?

Nein, in dem Beispiel dient der Exit der 1. Position (also deren TP) als Referenzpunkt, wann/an welcher Stelle etwas mit der 2. Position geschehen soll. Wenn Du nur eine Position hast, dann brauchst Du einen eigenen Referenzpunkt - z.B. wenn der Close über dem nächsten PSARpunkt (bei Long) liegt oder er 20 Punkte über dem Eröffnungskurs liegt oder was Dir sonst noch so einfällt.

Zitat:

Zitat von Karabiner (Beitrag 40598)
Also 2 Positionen zum selben Preis .. beide den selben SL .. 1.Position sagen wir TP bei 10€ und 2. Position TP bei 15€ ... wenn jetzt die 1. Position die den TP bei 10€ erreicht hat und dadurch geschlossen wird .. entfernen des TP der 2. Position bei 15€ ... und jetzt arbeitet der Trailing Stop und zieht den SL nach ... aber warum macht er das ?

Das liegt an den Bedingungen:
Code:

if    (Bedingung-1 erfüllt) { mache dieses; } // wenn nicht, nächste Zeile
else if(Bedingung-2 erfüllt) { mache jenes; } // wenn nicht, nächste Zeile
else if(Bedingung-3 erfüllt) { mache dies; } // wenn nicht, nächste Zeile
else                        { mache das; } // ansonsten das hier

Zitat:

Zitat von Karabiner (Beitrag 40598)
arbeitet das programm zyklisch von "oben nach unten" ?

jein. Variablen müssen vor der Benutzung bestimmt werden; Bedingungen, Schleifen und sonstiges (siehe oben) gehen immer von oben nach unten; Funktionen (wie OnDeinit, OnCalculate oder selbstgeschriebene wie z.B. FuncCheckOpenLongs) können irgendwo stehen (und da auf ihren Aufruf warten).
Ich hoffe, das beantwortet Deine Fragen. AVT

Karabiner 20.03.18 18:05

Hallo AVT,

danke für deine Antwort. :)

Deine Tips waren super nützlich für mich, allerdings stehe ich vor einem neuen Problem.

Wenn ich meinen zusammengeschusterten EA im Backtest laufen lasse, dann hab ich in der LongOrder den TakeProfit und definitv jetzt meinen TrailingStop. freu

Aber nun hab ich das Problem das ich keine TP´s und SL´s mehr bei der ShortOrder bekomme. Seltsam find ich es, da der TP für die LongOrder erst nach dem TrailingStop Programmteil bearbeitet wird und da funktioniert es.

Könntest Du mir da vielleicht bitte noch einmal helfen?

Code:

//Stopp Loss Long setzen
{
  if (OrderSelect(LongOrder,SELECT_BY_TICKET)==true)
      {
          if(OrderCloseTime() ==0 && OrderStopLoss() ==0 )
          {
         
              StoppLoss= NormalizeDouble (OrderOpenPrice()/(1+(SL_prozent/100)),Digits);
              OrderAngepasst = OrderModify (OrderTicket(),OrderOpenPrice(),StoppLoss,OrderTakeProfit(),0,Yellow);
       
          }

  else if(OrderCloseTime () == 0 && OrderAngepasst == true)
  {
 
  O_Sym = OrderSymbol();
  O_Point = MarketInfo(O_Sym,MODE_POINT);  // Größe eines Punktes im Symbol der Order
 
  if(_Digits == 3 || _Digits == 5)
      O_Point = O_Point*10;
 
  if(OrderType() == OP_BUY)
  {
      O_Price = MarketInfo(O_Sym,MODE_BID);  // Aktuellen Preis des entsprechenden Symbols
     
      if(OrderStopLoss() < O_Price-((TrailingStop_Abstand+TrailingStop_Schritt) * O_Point))
      {
        if(!OrderModify(OrderTicket(),OrderOpenPrice(),O_Price-(TrailingStop_Abstand*O_Point),OrderTakeProfit(),0))
            Alert("Order #",IntegerToString(OrderTicket())," konnte nicht modifiziert werden! Fehler Nr: ",IntegerToString(GetLastError()));
      } 
  }
  else if(OrderType() == OP_SELL)
  {
      O_Price = MarketInfo(O_Sym,MODE_ASK);  // Aktuellen Preis des entsprechenden Symbols
     
      if(OrderStopLoss() > O_Price+((TrailingStop_Abstand+TrailingStop_Schritt) * O_Point))
      {
        if(!OrderModify(OrderTicket(),OrderOpenPrice(),O_Price+(TrailingStop_Abstand*O_Point),OrderTakeProfit(),0))
            Alert("Order #",IntegerToString(OrderTicket())," konnte nicht modifiziert werden! Fehler Nr: ",IntegerToString(GetLastError()));
      }
  }

      }
//Stopp Loss Short setzen
 if (OrderSelect(ShortOrder,SELECT_BY_TICKET)==true)
      {
          if(OrderCloseTime() ==0 && OrderStopLoss() ==0)
          {
                        StoppLoss= NormalizeDouble (OrderOpenPrice()*(1+(SL_prozent/100)),Digits);
              OrderAngepasst = OrderModify (OrderTicket(),OrderOpenPrice(),StoppLoss,OrderTakeProfit(),0,Yellow);
   
}}
    else if(OrderCloseTime () == 0 && OrderAngepasst == true)
  {
 
  O_Sym = OrderSymbol();
  O_Point = MarketInfo(O_Sym,MODE_POINT);  // Größe eines Punktes im Symbol der Order
 
  if(_Digits == 3 || _Digits == 5)
      O_Point = O_Point*10;
 
  if(OrderType() == OP_SELL)
  {
      O_Price = MarketInfo(O_Sym,MODE_ASK);  // Aktuellen Preis des entsprechenden Symbols
     
      if(OrderStopLoss() > O_Price+((TrailingStop_Abstand+TrailingStop_Schritt) * O_Point))
      {
        if(!OrderModify(OrderTicket(),OrderOpenPrice(),O_Price+(TrailingStop_Abstand*O_Point),OrderTakeProfit(),0))
            Alert("Order #",IntegerToString(OrderTicket())," konnte nicht modifiziert werden! Fehler Nr: ",IntegerToString(GetLastError()));
      } 
  }
  else if(OrderType() == OP_BUY)
  {
      O_Price = MarketInfo(O_Sym,MODE_BID);  // Aktuellen Preis des entsprechenden Symbols
     
      if(OrderStopLoss() < O_Price-((TrailingStop_Abstand+TrailingStop_Schritt) * O_Point))
      {
        if(!OrderModify(OrderTicket(),OrderOpenPrice(),O_Price-(TrailingStop_Abstand*O_Point),OrderTakeProfit(),0))
            Alert("Order #",IntegerToString(OrderTicket())," konnte nicht modifiziert werden! Fehler Nr: ",IntegerToString(GetLastError()));
      }
  }

      }

Ich hab irgendwo gelesen das man z.B. bei der LongOrder den TrailSL mit OrderType() == OP_BUY modifizieren muss, aber unbedingt auch den OP_SELL einbauen soll. ??? Keine Ahnung ob das richtig ist ???

Gruß
Karabiner

AVT 21.03.18 12:41

Zitat:

Zitat von Karabiner (Beitrag 40614)
Ich hab irgendwo gelesen das man z.B. bei der LongOrder den TrailSL mit OrderType() == OP_BUY modifizieren muss, aber unbedingt auch den OP_SELL einbauen soll.

Wenn Dein EA nur Long geht (gibt es ja auch), dann mußt Du Dich auch nur um die Long Orders kümmern, also OrderType()==OP_BUY; wenn Du aber einen EA hast, der beide Richtungen tradet, dann mußt Du Dich natürlich auch um die Short Orders kümmern OrderType()==OP_SELL.

Zitat:

Zitat von Karabiner (Beitrag 40614)
Aber nun hab ich das Problem das ich keine TP´s und SL´s mehr bei der ShortOrder bekomme. Seltsam find ich es, da der TP für die LongOrder erst nach dem TrailingStop Programmteil bearbeitet wird und da funktioniert es.

Da läuft einiges schief mit Deinen Klammern. Das solltest Du erst mal überprüfen. Mir hilft ein Aufbau wie dieser, ziemlich schnell zu sehen was wo wann hingehört oder fehlt:
Code:

if    (Bedingung1)
{
      if    (BedingungA)
      {
      } //== if(BedingungA)
      else if(BedingungB)
      {
      } //== else if(BedingungB)
     
} // == if (Bedingung1)
else if(Bedingung2)
{
  if(BedingungA1)
  {
      if(BedingungA11)
      {
        if(BedingungA111)
        {
            mache was;
        } // == if(BedingungA111)
      } // == if(BedingungA11)
  } // == if(BedingungA1)
 
} // == else if(Bedingung)

Ich setze also (abweichend zu anderen) die öffnende Klammer immer direkt unter den Anfang der Bedingung und die schließende auf genau dieselbe Ebene , hat den Vorteil, daß ich den Cursor nur noch hinter die Klammer setzen muß und dann mit der Pfeil-runter-Taste nach unten gehe, um zu sehen, wo Schluß ist. Die schließende Klammer kriegt meistens einen Kommentar, was geschlossen wird, das liest sich mit der folgenden Bedingung dann wie ein Satz (und man weiß wo man ist). Und alles was in der Bedingung gemacht werden soll, wird um einen TAB oder eine feste Anzahl Leerzeichen eingerückt.
Vielleicht hilft Dir das schon, Ordnung in die Bedingungen zu bringen. AVT

next user 21.03.18 13:07

Zitat:

Zitat von Karabiner (Beitrag 40614)
Ich hab irgendwo gelesen das man z.B. bei der LongOrder den TrailSL mit OrderType() == OP_BUY modifizieren muss, aber unbedingt auch den OP_SELL einbauen soll. ??? Keine Ahnung ob das richtig ist ???

Nein! Wie soll denn OP_SELL bei ner LongOrder zutreffen?
Wenn du etwas machen möchtest, das eine OP_SELL-Abfrage erfordert, dann brauchst du es.
Aber bitte nicht NUR, weil es irgendwo zu lesen war, du aber keine Verwendung dafür hast.

=== === === === === === === === === === === ===

Ich habe mir mal deinen Code angesehen und gleich mal falsche Klammersetzung gefunden.
Wenn das wirklich der ausgeführte Code von dir ist, so müsste da einiges an Fehlverhalten sein.
Auch sind "O_Sym, O_Point & O_Price" nur nötig, wenn sich Ordersymbol und aktuelles Symbol unterscheiden.
Bei dir höre ich aber nirgendwo raus, das dein "zusammengeschusteter" EA Orders eines anderen Symbols managed.
Auch sind in deinem Code sonst noch andere, unnötige Sachen.

Muss dein SL eigentlich so aussehen? OrderOpenPrice() / 1,002 ???
Und wieso setzt du nicht schon bei der Ordereröffnung einen SL, sondern erst mit OrderModify() ?

Dein Code mal etwas zusammengefasst:
Code:

// StopLoss Long
if(OrderSelect(LongOrder,SELECT_BY_TICKET))
{
  if(OrderCloseTime() == 0)
  {
      if(OrderStopLoss() == 0)
      {
        StoppLoss = NormalizeDouble(OrderOpenPrice() / (1+(SL_prozent/100)),Digits);
       
        if(OrderModify(OrderTicket(),OrderOpenPrice(),StoppLoss,OrderTakeProfit(),0,Yellow))
            // Fehler...
      }
      else
      {
        // Hier ggf. deine O_... Variablen, falls wirklich unterschiedliche
        // Symbole vom EA gemanaged werden, ansonsten:
       
        double O_Point = Point;
       
        if(Digits == 3 || Digits == 5)
            O_Point *= 10;
       
        if(OrderStopLoss() < Bid - ((TrailingStop_Abstand+TrailingStop_Schritt) * O_Point))
        {
            if(!OrderModify(OrderTicket(),OrderOpenPrice(),Bid - TrailingStop_Abstand * O_Point,OrderTakeProfit(),0))
              Alert("Order #",IntegerToString(OrderTicket())," konnte nicht modifiziert werden! Fehler Nr: ",IntegerToString(GetLastError()));
        }
      }
  }
  else
      // Order bereits geschlossen
}

// StopLoss Short
if(OrderSelect(ShortOrder,SELECT_BY_TICKET))
{
  if(OrderCloseTime() == 0)
  {
      if(OrderStopLoss() == 0)
      {
        StoppLoss = NormalizeDouble(OrderOpenPrice() / (1+(SL_prozent/100)),Digits);
       
        if(OrderModify(OrderTicket(),OrderOpenPrice(),StoppLoss,OrderTakeProfit(),0,Yellow))
            // Fehler...
      }
      else
      {
        // Hier ggf. deine O_... Variablen, falls wirklich unterschiedliche
        // Symbole vom EA gemanaged werden, ansonsten:
       
        double O_Point = Point;
       
        if(Digits == 3 || Digits == 5)
            O_Point *= 10;
       
        if(OrderStopLoss() > Ask + ((TrailingStop_Abstand+TrailingStop_Schritt) * O_Point))
        {
            if(!OrderModify(OrderTicket(),OrderOpenPrice(),Ask + TrailingStop_Abstand *O_Point,OrderTakeProfit(),0))
              Alert("Order #",IntegerToString(OrderTicket())," konnte nicht modifiziert werden! Fehler Nr: ",IntegerToString(GetLastError()));
        }
      }
  }
  else
      // Order bereits geschlossen
}


Karabiner 21.03.18 18:02

Hallo AVT und next user


Zitat:

Zitat von AVT (Beitrag 40627)
Da läuft einiges schief mit Deinen Klammern. Das solltest Du erst mal überprüfen. Mir hilft ein Aufbau wie dieser, ziemlich schnell zu sehen was wo wann hingehört oder fehlt:

Zitat:

Zitat von next user (Beitrag 40628)
Ich habe mir mal deinen Code angesehen und gleich mal falsche Klammersetzung gefunden.

Das mit dem geordneten und strukturierten Code weiß ich :o und liegt an meiner Disziplin. Durch das copy and paste aus meinem Ablage EA , in dem ich alle Versuche ablege, sieht es dann so wirr aus.

Was ich nur nicht verstehe ist, wie ihr es meint? Der Compiler sagte 0 Warnungen und 0 Fehler .. ich vermute ich hatte bei einer Bedingung zu viele geschweifte Klammern gesetzt ? aber in der Anzahl für den Compiler war alles gut.

Zitat:

Zitat von AVT (Beitrag 40627)
Ich setze also (abweichend zu anderen) die öffnende Klammer immer direkt unter den Anfang der Bedingung und die schließende auf genau dieselbe Ebene , hat den Vorteil, daß ich den Cursor nur noch hinter die Klammer setzen muß und dann mit der Pfeil-runter-Taste nach unten gehe, um zu sehen, wo Schluß ist. Die schließende Klammer kriegt meistens einen Kommentar, was geschlossen wird, das liest sich mit der folgenden Bedingung dann wie ein Satz (und man weiß wo man ist). Und alles was in der Bedingung gemacht werden soll, wird um einen TAB oder eine feste Anzahl Leerzeichen eingerückt.
Vielleicht hilft Dir das schon, Ordnung in die Bedingungen zu bringen. AVT

Das muss ich mir unbedingt angewöhnen :)

Zitat:

Zitat von next user (Beitrag 40628)
Wenn das wirklich der ausgeführte Code von dir ist, so müsste da einiges an Fehlverhalten sein.
Auch sind "O_Sym, O_Point & O_Price" nur nötig, wenn sich Ordersymbol und aktuelles Symbol unterscheiden.
Bei dir höre ich aber nirgendwo raus, das dein "zusammengeschusteter" EA Orders eines anderen Symbols managed.
Auch sind in deinem Code sonst noch andere, unnötige Sachen.

Muss dein SL eigentlich so aussehen? OrderOpenPrice() / 1,002 ???
Und wieso setzt du nicht schon bei der Ordereröffnung einen SL, sondern erst mit OrderModify() ?

ja, hatte ja nicht funktioniert :D

das stimmt schon mit dem Symbol was du schreibst .. bei der Eröffnung OrderSend wird Symbol () benutzt und so wie ich es verstehe benutzt er dann genau das Symbol des Charts

Code:

extern double HandelLots = 0.1, SL_prozent = 0.2, TP_prozent = 1.0;
extern int MagicNummer = 12345;
extern int LongOrder, ShortOrder;

daher kommt die 1,002

weil ich das EA Grundgerüst aus einer Videoanleitung habe und es dort so gemacht wurde und ich .. also sagen wir im Karate gibt es vom weißen Gürtel bis zum Schwarzen und ich hab nen Seil um :(

Danke für eure Hilfe

Gruß
Karabiner

Karabiner 21.03.18 18:02

Ps.: funktioniert jetzt :)


Alle Zeitangaben in WEZ +2. Es ist jetzt 19:39 Uhr.

Powered by vBulletin® Version 3.8.5 (Deutsch)
Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
SEO by vBSEO 3.6.1
Powered by vBCMS® 2.7.0 ©2002 - 2024 vbdesigns.de
Copyright ©2009 - 2023 by Expert-Advisor.com - Das Metatrader Forum