Abrir ordem oposta - página 2

 

Você não pode fazer isto para ajustar a Slippage para Corretores de 4/5 dígitos, simplesmente não faz sentido.

O Slippage DEVE ser um int, portanto um número inteiro, para um Slippage de 4 dígitos está em Pips, portanto Slippage = 3 significa 3 Pips, para um Slippage de 5 dígitos está em pontos, portanto Slippage = 3 significa 3 pontos ou 0.3 Pips. Assim, para compensar, para um Corretor de 5 dígitos o deslize deve ser multiplicado por dez dando 30 . . . 30 pontos = 3 Pips.

Portanto, este código está errado . .

int init()
   {
   if (Digits ==3 || Digits ==5) pt = 10 * Point;
   else pt = Point;
   Slippage = Slippage * pt;    
   }
 

Experimente esta versão modificada de suafunção OpenOppositeOrder() . .

void OpenOppositeOrder() 
   {
   int Op;  
 
   for(int Counter = OrdersTotal()-1; Counter >= 0; Counter--)
      {
      if(OrderSelect(Counter,SELECT_BY_POS,MODE_TRADES))  // only continue if the OrderSelect() worked
         {
         if(OrderSymbol() == Symbol()&& OrderMagicNumber() == MagicNumber)
            {
            Op = OrderType();

            if(Op == OP_BUY && Bid < OrderOpenPrice())
               {      
               Ticket = OrderSend(Symbol(), OP_SELL, LotSize, Bid, Slippage, 0, 0, "Sell Order", MagicNumber, 0, Red);
               if(Ticket > 0) 
                  {
                  Print("Opposite Sell order placed # ", Ticket);
                  AddLimitsSell();
                  }
               else
                  {
                  Print("Order Send failed, error # ", GetLastError() );
                  }
               }
               
            if(Op == OP_SELL && Ask > OrderOpenPrice())
               {      
               Ticket = OrderSend(Symbol(), OP_BUY, LotSize, Ask, Slippage, 0, 0, "Buy Order", MagicNumber, 0, Green);
               if(Ticket > 0)
                  {
                  Print("Opposite Buy order placed # ", Ticket);
                  AddLimitsBuy();
                  }
               else
                  {  
                  Print("Order Send failed, error # ", GetLastError() );
                  }   
               }
            }
         }
      }
   }
 
RaptorUK:

Experimente esta versão modificada de sua função OpenOppositeOrder() . .


Olá RaptorUk,

Antes de tudo, obrigado pela ajuda fornecida até o momento. Agora a EA começa a trabalhar. Fiz outras modificações sobre como fechar tudo se uma ordem tem lucro e isso é bom, mas como vocês já viram e prevêem para este trabalho estratégico é necessário que a ordem que atinge lucro tenha o tamanho do lote aumentado para compensar as ordens anteriores. com isso em mente, introduzi um código para fazer isso. por isso estou lidando com uma confusão aqui. Preciso confirmar se a última ordem teve lucro ou não e quero usar OrderProfit() de forma a ajustar o próximo tamanho de lote da ordem, mas, não preciso fechar a ordem anterior para obter essa informação?

Aqui está o código para abrir uma ordem oposta que está funcionando bem (graças a você) onde eu introduzo o código extra para descobrir se a ordem anterior que está aberta tem lucro. Estou no caminho certo para conseguir isso?

Obrigado.

Luis

 void OpenOppositeOrder() 
 {
// LastOrder Loss Compensation 
   int Orders;
   Orders= OrdersTotal();
   if (Orders>0)
   {  
    for(i=0;i<Orders;i++)
   {
    OrderSelect(i,SELECT_BY_POS,MODE_TRADES);
    if(OrderSymbol()==Symbol()&& OrderMagicNumber()== MagicNumber)
   {
    lastprofit = OrderProfit();
    lastlot = OrderLots();
   }
  }
 }
  mlots=0;
  if (lastprofit<0)mlots=NormalizeDouble(lastlot*Multiplier,Digits);
  else mlots=LotSize;
 
//+------------------------------------------------------------------+ 
//Open Opposite Order 
   int Op;  
 
   for(int Counter = OrdersTotal()-1; Counter >= 0; Counter--)
      {
      if(OrderSelect(Counter,SELECT_BY_POS,MODE_TRADES))  
         {
         if(OrderSymbol() == Symbol()&& OrderMagicNumber() == MagicNumber)
            {
            Op = OrderType();

            if(Op == OP_BUY && Bid < OrderOpenPrice())
               {  
               if(Martingale)ilots=mlots;else ilots=LotSize; 
               Ticket = OrderSend(Symbol(), OP_SELL, ilots, Bid, UseSlippage, 0, 0, "Sell Order", MagicNumber, 0, Red);
               if(Ticket > 0) 
                  {
                  Print("Opposite Sell order placed # ", Ticket);
                  AddLimitsSell();
                  }
               else
                  {
                  Print("Order Send failed, error # ", GetLastError() );
                  }
               }
               
            if(Op == OP_SELL && Ask > OrderOpenPrice())
               { 
               if(Martingale)ilots=mlots;else ilots=LotSize;
               Ticket = OrderSend(Symbol(), OP_BUY, ilots, Ask, UseSlippage, 0, 0, "Buy Order", MagicNumber, 0, Green);
               if(Ticket > 0)
                  {
                  Print("Opposite Buy order placed # ", Ticket);
                  AddLimitsBuy();
                  }
               else
                  {  
                  Print("Order Send failed, error # ", GetLastError() );
                  }   
               }
            }
         }
      }
   }
 
luisneves:


Olá RaptorUk,

Antes de tudo, obrigado pela ajuda fornecida até o momento. Agora a EA começa a trabalhar. Fiz outras modificações sobre como fechar tudo se uma ordem tem lucro e isso é bom, mas como vocês já viram e prevêem para este trabalho estratégico é necessário que a ordem que atinge lucro tenha o tamanho do lote aumentado para compensar as ordens anteriores. com isso em mente, introduzi um código para fazer isso. por isso, estou lidando com uma confusão aqui. Preciso confirmar se a última ordem teve lucro ou não e quero usar OrderProfit() de forma a ajustar o próximo tamanho de lote da ordem, mas, não preciso fechar a ordem anterior para obter essa informação?

Aqui está o código para abrir uma ordem oposta que está funcionando bem (graças a você) onde eu introduzo o código extra para descobrir se a ordem anterior que está aberta tem lucro. Estou no caminho certo para conseguir isso?

Suspeito que isso lhe causará problemas ...

mlots = NormalizeDouble(lastlot * Multiplier, Digits);

por exemplo, se o resultado for 1.12316734 lotes, seu NormalizeDouble() no par de 5 dígitos o mudará para1.12316 e isto não estará de acordo com a exigência do Passo de Lote . . você precisa usar alguma matemática para fazer de seu tamanho de lote modificado um múltiplo de Lot Step MarketInfo(Symbol(),MODE_LOTSTEP)

 
RaptorUK:

Suspeito que isso lhe causará problemas ...

por exemplo, se o resultado for 1.12316734 lotes, seu NormalizeDouble() no par de 5 dígitos o mudará para1.12316 e isto não estará de acordo com a exigência do Passo de Lote . . você precisa usar alguma matemática para fazer de seu tamanho de lote modificado um múltiplo de Lot Step MarketInfo(Symbol(),MODE_LOTSTEP)


Olá RaptorUK,

Com relação ao seu conselho de procurar manter meu tamanho de lote um múltiplo de Passo de Lote, estou procurando me documentar sobre o assunto.

Agora tenho outro assunto (mais um...)

Para abrir os pedidos acima e abaixo do preço atual quero usar uma linha onde uma vez que o Ea comece a funcionar eu comparo o preço com a linha que ainda está.

Um primeiro problema vem; como posso comparar a linha com uma diferença no preço?

Aqui está o código que eu tenho até agora. Aqui como posso dar o nome para comparar porque se eu colocar iHigh após a linha de preço, simplesmente não funciona.

Obrigado de antemão por qualquer pista nestas questões.

Luis

priceline=iHigh(Symbol(),0,0);
 ObjectCreate("highline",OBJ_HLINE,0,0,Bid); 
 ObjectSet("highline",OBJPROP_COLOR,LimeGreen);
 ObjectSet("highline",OBJPROP_WIDTH,1);
 WindowRedraw();

Isto parece não funcionar em absoluto (...)

if(Bid > priceline+Distance*pt)                      
                {       
// Open buy order

                            while(IsTradeContextBusy()) Sleep(10);
                                 RefreshRates();        
                       
             Ticket=OrderSend(Symbol(),OP_BUY,LotSize,Ask,UseSlippage,0,0,"Buy Order",MagicNumber,0,Green);
             if(Ticket>0)AddLimitsBuy();
            }

Coloquei aqui o objeto deletado, porque preciso que a linha seja deletada com o fechamento de todos os pedidos. estou correto?

void CloseAll()
      {
         int i,Op,Error;
         int Total=OrdersTotal();
     
         if(Total>0)
         {
         for(int pos=OrdersTotal()-1;pos>=0;pos--)
         if(OrderSelect(pos,SELECT_BY_POS)
         && OrderMagicNumber()==MagicNumber && OrderSymbol()==Symbol())
         {
         Op=OrderType();
         if(Op==OP_BUY)
         {
         OrderClose(OrderTicket(),OrderLots(),Bid, UseSlippage, Yellow);
         }
         if(Op==OP_SELL)
         {
         OrderClose(OrderTicket(),OrderLots(),Ask, UseSlippage, Yellow);
         }
         else
         {
         ObjectDelete("highline");
         }
        }
       }
      }
 
luisneves:

Isto parece não funcionar em absoluto (...)

Coloquei aqui o objeto deletado, porque preciso que a linha seja deletada com o fechamento de todos os pedidos. estou correto?

OK, eu acho que entendo o que você quer fazer, você quer verificar onde Bid é comparado com sua linha, para fazer isso você precisa obter a posição da linha . . use ObjectGet() com o nome do objeto e índice de propriedade do objetoOBJPROP_TIME1 isto retornará o preço ao qual a linha é colocada.

Sua chamada ObjectDelete() me parece OK. Eu particularmente não gosto do uso de ObjectsDeleteAll() Eu acho que é preguiçoso e perigoso . ... ou no mínimo inconveniente para os outros.

 
RaptorUK:

OK, eu acho que entendo o que você quer fazer, você quer verificar onde Bid é comparado com sua linha, para fazer isso você precisa obter a posição da linha . . use ObjectGet() com o nome do objeto e índice de propriedade do objetoOBJPROP_TIME1 isto retornará o preço ao qual a linha é colocada.

Sua chamada ObjectDelete() me parece OK.


Olá RaptorUK,

Estou tentando fechar todas as ordens se uma fechar com lucro, mas quando isso acontece uma ordem pendente ainda está aberta, no entanto, a instrução para fechar está incluída na função CloseAll(). Alguma pista sobre este assunto ?

Agradecemos antecipadamente por qualquer ajuda que você possa dar.

Luis

int GoToClose()
 {
  int pos;  
 {
  for(int Profit=OrdersTotal()-1;pos>=0;pos--)
  if(OrderSelect(Profit,SELECT_BY_POS)
  && OrderMagicNumber()==MagicNumber && OrderSymbol()==Symbol()
  && OrderProfit()+OrderSwap()+OrderCommission()>0||OrdersTotal()> MaxOrders)CloseAll();  
 }
}
//+---------------------------------------------------------------------------+  
      void CloseAll()
      {
         int Op,Error;
                    
         for(int pos=OrdersTotal()-1;pos>=0;pos--)
         if(OrderSelect(pos,SELECT_BY_POS)
         && OrderMagicNumber()==MagicNumber && OrderSymbol()==Symbol())
         {
         Op=OrderType();
         if(Op==OP_BUY)
         {
         RefreshRates();
         OrderClose(OrderTicket(),OrderLots(),Bid, UseSlippage, Yellow);
         }
         if(Op==OP_SELL)
         {
         RefreshRates();
         OrderClose(OrderTicket(),OrderLots(),Ask, UseSlippage, Yellow);
         }
         if(Op==OP_SELLSTOP||OP_BUYSTOP||OP_SELLLIMIT||OP_BUYLIMIT)
         {
         RefreshRates();
         OrderDelete(OrderTicket());
         }
         else Print("Error opening BUY Stop Order : ",GetLastError());         
         }
        }             
 
luisneves:


Olá RaptorUK,

Estou tentando fechar todas as ordens se uma fechar com lucro, mas quando isso acontece uma ordem pendente ainda está aberta, no entanto, a instrução para fechar está incluída na função CloseAll(). Alguma pista sobre este assunto ?

Você precisa entender como funcionam as expressões . . . você não pode fazer isso . .

if(Op == OP_SELLSTOP || OP_BUYSTOP || OP_SELLLIMIT || OP_BUYLIMIT)

é uma situação semelhante a esta, mas não exatamente a mesma:https://www.mql5.com/en/forum/141790


O que é o resultado de . . .

WhatValue = (5  || 4  ||  3  ||  2 );

|| é um operador boleano, portanto só trabalha com bools . .


isto resulta em um valor resultante de bool . .

( Op == OP_SELLSTOP )

. . . se você quiser usar um operador um pouco sobre seus valores, então você pode usar isto . .

int WhatValue = (5  | 4  |  3  |  2 );

. . mas não é o que você está tentando fazer.

 
RaptorUK:

Você precisa entender como as expressões funcionam . . . você não pode fazer isso . .

é uma situação semelhante a esta, mas não exatamente a mesma:https://www.mql5.com/en/forum/141790


O que é o resultado de . . .

|| é um operador boleano, portanto só trabalha com bools . .


isto resulta em um valor resultante de bool . .

. . . se você quiser usar um operador um pouco sobre seus valores, então você pode usar isto . .

. . mas não é o que você está tentando fazer.


Olá RaptorUK,

Estou vendo, mas agora com isso em mente, modifiquei o código e a ordem pendente ainda lá...

void CloseAll()
      {
         int Op,Error;
                    
         for(int pos=OrdersTotal()-1;pos>=0;pos--)
         if(OrderSelect(pos,SELECT_BY_POS)
         && OrderMagicNumber()==MagicNumber && OrderSymbol()==Symbol())
         {
         Op=OrderType();
         if(Op==OP_BUY)
         {
         RefreshRates();
         OrderClose(OrderTicket(),OrderLots(),Bid, UseSlippage, Yellow);
         }
         if(Op==OP_SELL)
         {
         RefreshRates();
         OrderClose(OrderTicket(),OrderLots(),Ask, UseSlippage, Yellow);
         }
         if(Op==OP_SELLSTOP)
         {
         RefreshRates();
         OrderDelete(OrderTicket());
         }
         if(Op==OP_BUYSTOP)
         {
         RefreshRates();
         OrderDelete(OrderTicket());
         }
         else Print("Error opening BUY Stop Order : ",GetLastError());         
         }
        }        
 
luisneves:


Olá RaptorUK,

Estou vendo, mas agora com isso em mente, modifiquei o código e a ordem pendente ainda lá...

Pode ser se tiver um número mágico diferente doMagicNumber ou se for para um símbolo diferente do símbolo em que a EA está rodando ou se for um OP_SELLLIMIT ou OP_BUYLIMIT . . também, você precisa verificar os valores de retorno de suas chamadas OrderDelete() e OrderClose() .

Por que você precisa ligar para RefreshRates() ? eu não quero dizer se livrar deles, mas você pode explicar porque você está ligando para RefreshRates() onde você está ?


O que são valores de retorno de função ? Como eu os utilizo ?

Razão: