Upload DarvasBoxXAUUSD

This commit is contained in:
zhutoutoutousan
2025-04-28 20:19:19 +08:00
parent 66446c6053
commit 9de36a9d0d
3 changed files with 476 additions and 0 deletions
+440
View File
@@ -0,0 +1,440 @@
//+------------------------------------------------------------------+
//| DarvasBox.mq5 |
//| Copyright 2024, MetaQuotes Ltd. |
//| https://www.mql5.com |
//+------------------------------------------------------------------+
#property copyright "Copyright 2024, MetaQuotes Ltd."
#property link "https://www.mql5.com"
#property version "1.00"
#property strict
#include <Trade\Trade.mqh>
#include <Indicators\Trend.mqh>
#include <Indicators\Volumes.mqh>
// Input parameters
input int BoxPeriod = 165; // Period for Darvas Box calculation
input double BoxDeviation = 25140; // Box deviation in points
input int VolumeThreshold = 938; // Minimum volume for confirmation
input double StopLoss = 1665; // Stop loss in points (increased for BTCUSD)
input double TakeProfit = 3685; // Take profit in points (increased for BTCUSD)
input bool EnableLogging = false; // Enable detailed logging
input color BoxColor = clrBlue; // Color for Darvas Box
input int BoxWidth = 1; // Width of box lines
// Trend confirmation parameters
input ENUM_TIMEFRAMES TrendTimeframe = PERIOD_H2; // Timeframe for trend analysis
input int MA_Period = 125; // Moving Average period for trend
input ENUM_MA_METHOD MA_Method = MODE_EMA; // Moving Average method
input ENUM_APPLIED_PRICE MA_Price = PRICE_WEIGHTED; // Price type for MA
input double TrendThreshold = 4.94; // Trend strength threshold
// Volume analysis parameters
input int VolumeMA_Period = 110; // Period for Volume MA
input double VolumeThresholdMultiplier = 1.5; // Volume spike threshold
// Global variables
double boxHigh = 0;
double boxLow = 0;
bool boxFormed = false;
datetime lastBoxTime = 0;
string boxName = "DarvasBox_";
double minStopLevel = 0;
double point = 0;
CTrade trade;
ulong magicNumber = 135790;
// Indicator handles
int maHandle;
int volumeHandle;
//+------------------------------------------------------------------+
//| Expert initialization function |
//+------------------------------------------------------------------+
int OnInit()
{
// Initialize indicators and variables
boxHigh = 0;
boxLow = 0;
boxFormed = false;
lastBoxTime = 0;
// Get symbol properties
point = SymbolInfoDouble(_Symbol, SYMBOL_POINT);
minStopLevel = SymbolInfoInteger(_Symbol, SYMBOL_TRADE_STOPS_LEVEL) * point;
// Initialize indicators
maHandle = iMA(_Symbol, TrendTimeframe, MA_Period, 0, MA_Method, MA_Price);
volumeHandle = iVolumes(_Symbol, PERIOD_CURRENT, VOLUME_TICK);
if(maHandle == INVALID_HANDLE || volumeHandle == INVALID_HANDLE)
{
Print("Error creating indicators");
return(INIT_FAILED);
}
// Configure trade object
trade.SetDeviationInPoints(10);
trade.SetTypeFilling(ORDER_FILLING_IOC);
trade.SetAsyncMode(false);
trade.SetExpertMagicNumber(magicNumber);
if(EnableLogging)
{
Print("Darvas Box Expert Advisor initialized");
Print("Symbol: ", _Symbol);
Print("Point: ", point);
Print("Minimum Stop Level: ", minStopLevel);
}
// Delete any existing box objects
ObjectsDeleteAll(0, boxName);
return(INIT_SUCCEEDED);
}
//+------------------------------------------------------------------+
//| Draw Darvas Box on chart |
//+------------------------------------------------------------------+
void DrawDarvasBox()
{
if(!boxFormed) return;
datetime time1 = iTime(_Symbol, PERIOD_H1, BoxPeriod);
datetime time2 = iTime(_Symbol, PERIOD_H1, 0);
// Delete old box
ObjectsDeleteAll(0, boxName);
// Draw box
ObjectCreate(0, boxName + "Top", OBJ_TREND, 0, time1, boxHigh, time2, boxHigh);
ObjectCreate(0, boxName + "Bottom", OBJ_TREND, 0, time1, boxLow, time2, boxLow);
// Set box properties
ObjectSetInteger(0, boxName + "Top", OBJPROP_COLOR, BoxColor);
ObjectSetInteger(0, boxName + "Bottom", OBJPROP_COLOR, BoxColor);
ObjectSetInteger(0, boxName + "Top", OBJPROP_WIDTH, BoxWidth);
ObjectSetInteger(0, boxName + "Bottom", OBJPROP_WIDTH, BoxWidth);
ObjectSetInteger(0, boxName + "Top", OBJPROP_RAY_RIGHT, true);
ObjectSetInteger(0, boxName + "Bottom", OBJPROP_RAY_RIGHT, true);
}
//+------------------------------------------------------------------+
//| Calculate Darvas Box levels |
//+------------------------------------------------------------------+
void CalculateDarvasBox()
{
double high = 0;
double low = DBL_MAX;
// Find highest high and lowest low in the period
for(int i = 0; i < BoxPeriod; i++)
{
high = MathMax(high, iHigh(_Symbol, PERIOD_H1, i));
low = MathMin(low, iLow(_Symbol, PERIOD_H1, i));
}
double range = high - low;
double allowedRange = BoxDeviation * _Point;
if(EnableLogging)
{
Print("Box Calculation - High: ", high, " Low: ", low, " Range: ", range, " Allowed Range: ", allowedRange);
}
// Check if box is formed
if(range <= allowedRange)
{
boxHigh = high;
boxLow = low;
boxFormed = true;
lastBoxTime = iTime(_Symbol, PERIOD_CURRENT, 0);
// Draw the box
DrawDarvasBox();
if(EnableLogging)
Print("Box Formed - High: ", boxHigh, " Low: ", boxLow, " Time: ", lastBoxTime);
}
else
{
boxFormed = false;
// Delete box if it exists
ObjectsDeleteAll(0, boxName);
}
}
//+------------------------------------------------------------------+
//| Validate and adjust stop levels |
//+------------------------------------------------------------------+
bool ValidateStopLevels(double price, double &sl, double &tp, ENUM_ORDER_TYPE orderType)
{
double minSlDistance = MathMax(minStopLevel, StopLoss * point);
double minTpDistance = MathMax(minStopLevel, TakeProfit * point);
if(EnableLogging)
{
Print("Minimum SL Distance: ", minSlDistance);
Print("Minimum TP Distance: ", minTpDistance);
}
// Adjust stop loss
if(orderType == ORDER_TYPE_BUY)
{
sl = price - minSlDistance;
tp = price + minTpDistance;
if(EnableLogging)
{
Print("Buy Order Levels:");
Print("Entry: ", price);
Print("Stop Loss: ", sl);
Print("Take Profit: ", tp);
}
}
else // ORDER_TYPE_SELL
{
sl = price + minSlDistance;
tp = price - minTpDistance;
if(EnableLogging)
{
Print("Sell Order Levels:");
Print("Entry: ", price);
Print("Stop Loss: ", sl);
Print("Take Profit: ", tp);
}
}
return true;
}
//+------------------------------------------------------------------+
//| Check trend direction and strength |
//+------------------------------------------------------------------+
bool IsTrendFavorable(ENUM_ORDER_TYPE orderType)
{
double ma[];
ArraySetAsSeries(ma, true);
if(CopyBuffer(maHandle, 0, 0, 2, ma) <= 0)
return false;
double currentPrice = SymbolInfoDouble(_Symbol, SYMBOL_ASK);
double trendStrength = MathAbs(currentPrice - ma[0]) / point;
if(EnableLogging)
Print("Trend Strength: ", trendStrength);
if(orderType == ORDER_TYPE_BUY)
return (currentPrice > ma[0] && trendStrength > TrendThreshold);
else
return (currentPrice < ma[0] && trendStrength > TrendThreshold);
}
//+------------------------------------------------------------------+
//| Check volume conditions |
//+------------------------------------------------------------------+
bool CheckVolumeConditions()
{
double volumes[];
ArraySetAsSeries(volumes, true);
if(CopyBuffer(volumeHandle, 0, 0, VolumeMA_Period + 1, volumes) <= 0)
return false;
double volumeMA = 0;
for(int i = 1; i <= VolumeMA_Period; i++)
volumeMA += volumes[i];
volumeMA /= VolumeMA_Period;
double currentVolume = volumes[0];
double volumeRatio = currentVolume / volumeMA;
if(EnableLogging)
Print("Volume Ratio: ", volumeRatio);
return (volumeRatio > VolumeThresholdMultiplier);
}
//+------------------------------------------------------------------+
//| Place trade order |
//+------------------------------------------------------------------+
bool PlaceOrder(ENUM_ORDER_TYPE orderType, double price, double sl, double tp)
{
// Validate and adjust stop levels
if(!ValidateStopLevels(price, sl, tp, orderType))
{
if(EnableLogging)
Print("Invalid stop levels after adjustment");
return false;
}
// Check trend and volume conditions
if(!IsTrendFavorable(orderType))
{
if(EnableLogging)
Print("Trend not favorable for trade");
return false;
}
if(!CheckVolumeConditions())
{
if(EnableLogging)
Print("Volume conditions not met");
return false;
}
if(EnableLogging)
{
Print("Order Details:");
Print("Type: ", EnumToString(orderType));
Print("Price: ", price);
Print("Stop Loss: ", sl);
Print("Take Profit: ", tp);
}
bool result = false;
if(orderType == ORDER_TYPE_BUY)
{
result = trade.Buy(0.01, _Symbol, price, sl, tp, "Darvas Box Breakout");
}
else
{
result = trade.Sell(0.01, _Symbol, price, sl, tp, "Darvas Box Breakdown");
}
if(EnableLogging)
{
if(result)
Print((orderType == ORDER_TYPE_BUY ? "Buy" : "Sell"), " Order Placed Successfully");
else
Print((orderType == ORDER_TYPE_BUY ? "Buy" : "Sell"), " Order Failed - Error: ", trade.ResultRetcode(), " Description: ", trade.ResultRetcodeDescription());
}
return result;
}
//+------------------------------------------------------------------+
//| Expert tick function |
//+------------------------------------------------------------------+
void OnTick()
{
// Calculate new box levels
CalculateDarvasBox();
// Check for trading signals
if(boxFormed)
{
double currentPrice = SymbolInfoDouble(_Symbol, SYMBOL_ASK);
double currentVolume = iVolume(_Symbol, PERIOD_CURRENT, 0);
if(EnableLogging)
{
Print("Current Price: ", currentPrice, " Box High: ", boxHigh, " Box Low: ", boxLow);
Print("Current Volume: ", currentVolume, " Volume Threshold: ", VolumeThreshold);
}
// Check for breakout above box
if(currentPrice > boxHigh && currentVolume > VolumeThreshold)
{
if(EnableLogging)
Print("Breakout Signal Detected - Price above box high");
// Buy signal
if(PositionsTotal() == 0) // No existing positions
{
double sl = currentPrice - StopLoss * _Point;
double tp = currentPrice + TakeProfit * _Point;
if(EnableLogging)
Print("Preparing Buy Order - Price: ", currentPrice, " SL: ", sl, " TP: ", tp);
PlaceOrder(ORDER_TYPE_BUY, currentPrice, sl, tp);
}
else if(EnableLogging)
Print("Skipping Buy Signal - Position already exists");
}
// Check for breakdown below box
if(currentPrice < boxLow && currentVolume > VolumeThreshold)
{
if(EnableLogging)
Print("Breakdown Signal Detected - Price below box low");
// Sell signal
if(PositionsTotal() == 0) // No existing positions
{
double sl = currentPrice + StopLoss * _Point;
double tp = currentPrice - TakeProfit * _Point;
if(EnableLogging)
Print("Preparing Sell Order - Price: ", currentPrice, " SL: ", sl, " TP: ", tp);
PlaceOrder(ORDER_TYPE_SELL, currentPrice, sl, tp);
}
else if(EnableLogging)
Print("Skipping Sell Signal - Position already exists");
}
}
else if(EnableLogging)
Print("No Box Formed - Waiting for consolidation");
}
//+------------------------------------------------------------------+
//| Get last error description |
//+------------------------------------------------------------------+
string GetLastErrorDescription()
{
string errorDescription;
switch(GetLastError())
{
case 0: errorDescription = "No error"; break;
case 1: errorDescription = "No error, but result unknown"; break;
case 2: errorDescription = "Common error"; break;
case 3: errorDescription = "Invalid trade parameters"; break;
case 4: errorDescription = "Trade server is busy"; break;
case 5: errorDescription = "Old version of the client terminal"; break;
case 6: errorDescription = "No connection with trade server"; break;
case 7: errorDescription = "Not enough rights"; break;
case 8: errorDescription = "Too frequent requests"; break;
case 9: errorDescription = "Malfunctional trade operation"; break;
case 64: errorDescription = "Account disabled"; break;
case 65: errorDescription = "Invalid account"; break;
case 128: errorDescription = "Trade timeout"; break;
case 129: errorDescription = "Invalid price"; break;
case 130: errorDescription = "Invalid stops"; break;
case 131: errorDescription = "Invalid trade volume"; break;
case 132: errorDescription = "Market is closed"; break;
case 133: errorDescription = "Trade is disabled"; break;
case 134: errorDescription = "Not enough money"; break;
case 135: errorDescription = "Price changed"; break;
case 136: errorDescription = "Off quotes"; break;
case 137: errorDescription = "Broker is busy"; break;
case 138: errorDescription = "Requote"; break;
case 139: errorDescription = "Order is locked"; break;
case 140: errorDescription = "Long positions only allowed"; break;
case 141: errorDescription = "Too many requests"; break;
case 145: errorDescription = "Modification denied because order is too close to market"; break;
case 146: errorDescription = "Trade context is busy"; break;
case 147: errorDescription = "Expirations are denied by broker"; break;
case 148: errorDescription = "Amount of open and pending orders has reached the limit"; break;
case 149: errorDescription = "Hedging is prohibited"; break;
case 150: errorDescription = "Prohibited by FIFO rules"; break;
default: errorDescription = "Unknown error"; break;
}
return errorDescription;
}
//+------------------------------------------------------------------+
//| Expert deinitialization function |
//+------------------------------------------------------------------+
void OnDeinit(const int reason)
{
// Delete all box objects
ObjectsDeleteAll(0, boxName);
if(EnableLogging)
Print("Expert Advisor deinitialized - Reason: ", reason);
}
Binary file not shown.

After

Width:  |  Height:  |  Size: 239 KiB

+36
View File
@@ -8,6 +8,7 @@
- [3. RSI Reversal Asian EUR/USD](#3-rsi-reversal-asian-eurusd)
- [4. RSI CrossOver Reversal XAU/USD](#4-rsi-crossover-reversal-xauusd)
- [5. RSI Follow Reverse EMA CrossOver BTC/USD](#5-rsi-follow-reverse-ema-crossover-btcusd)
- [6. DarvasBoxXAUUSD](#6-darvasboxxauusd)
- [Strategy Rationale](#strategy-rationale)
- [RSI Reversal Strategy](#rsi-reversal-strategy)
- [RSI MidPoint Hijack Strategy](#rsi-midpoint-hijack-strategy)
@@ -183,6 +184,41 @@ InpCooldownPeriod = 24; // Cooldown Period in hours
<img src="RSIFollowReverseEMACrossOverBTCUSD/test-balance.jpg" alt="RSI Follow Reverse EMA CrossOver BTC/USD Test Balance" width="600"/>
</div>
### 6. DarvasBoxXAUUSD
- **Strategy**: Darvas Box breakout strategy for Gold trading
- **Key Features**:
- Implements the classic Darvas Box theory for trend identification
- Specifically optimized for Gold (XAU/USD) trading
- Features dynamic box size adjustment based on volatility
- Includes multiple timeframe analysis
- Implements strict risk management with configurable stop loss and take profit
- Features a visual panel showing real-time box levels and trading metrics
**Core Parameters:**
```mql5
// Box Settings
BoxPeriod = 20; // Box formation period
MinBoxSize = 50; // Minimum box size in pips
MaxBoxSize = 200; // Maximum box size in pips
VolatilityFactor = 1.5; // Volatility adjustment factor
// Risk Management
TakeProfitPips = 300; // Take profit in pips
StopLossPips = 150; // Stop loss in pips
MaxLotSize = 0.1; // Maximum lot size
MaxSpread = 1000; // Maximum allowed spread in pips
MaxDuration = 48; // Maximum trade duration in hours
// Timeframe Settings
PrimaryTF = PERIOD_H1; // Primary timeframe
SecondaryTF = PERIOD_H4; // Secondary timeframe for confirmation
```
**Test Balance Results:**
<div align="center">
<img src="DarvasBoxXAUUSD/test-balance.jpg" alt="Darvas Box XAU/USD Test Balance" width="600"/>
</div>
## Strategy Rationale
### RSI Reversal Strategy