//+------------------------------------------------------------------+ //| QuarterTheory_VIZION_BIAS_v3.3.mq5 | //| BIAS FILTERED | MA7 + MFIB + STOCH DIRECTION | //| Close Opposing Trades | Directional Flow | 300 Rule | //+------------------------------------------------------------------+ #property copyright "QuarterTheory x VIZION - BIAS FILTERED v3.3" #property version "3.30" #property strict #include CTrade Trade; //================ INPUT PARAMETERS ==================// input group "=== CORE SETTINGS ===" input int MagicNumber = 456789; input double Risk_Per_Trade = 1.2; input int Max_Trades_Per_Setup = 10; input int Max_Total_Trades = 100; input group "=== BIAS SYSTEM ===" input bool Use_Bias_Filter = true; // Use directional bias input bool Close_Opposing_On_Flip = true; // Close counter trades on bias flip input int Bias_Flip_Bars = 3; // Bars to confirm bias flip input group "=== MA SYSTEM ===" input int MA_1 = 7; // Heartbeat (primary bias) input int MA_2 = 14; input int MA_3 = 21; input int MA_4 = 50; input int MA_5 = 140; input int MA_6 = 230; input int MA_7 = 500; input int MA_8 = 1000; input int MA_9 = 1100; input int MA_10 = 1300; input int MA_Touch_Buffer = 100; input group "=== STOCHASTIC ===" input int Stoch_K_Period = 5; input int Stoch_D_Period = 3; input int Stoch_Slowing = 3; input double Stoch_Overbought = 70.0; input double Stoch_Oversold = 30.0; input group "=== MFIB SYSTEM ===" input int MFIB_Lookback = 500; input group "=== FIBONACCI ===" input int Lookback_Bars = 200; input bool Show_Levels = true; input group "=== 300 RULE EXIT SYSTEM ===" input int Initial_SL_Points = 300; input int BreakEven_Points = 300; input int Trailing_Distance_Points = 300; input int TP_Points = 1500; input int Partial_TP_Points = 900; input double Partial_TP_Percent = 33.0; //================ ENUMS ==================// enum BIAS_STATE { BIAS_STRONG_BULL, // Strong bullish bias BIAS_BULL, // Bullish bias BIAS_NEUTRAL, // Neutral - both ways BIAS_BEAR, // Bearish bias BIAS_STRONG_BEAR // Strong bearish bias }; enum SETUP_TYPE { SETUP_MA14_CROSS = 1, SETUP_MA50_BOUNCE = 2, SETUP_MA140_BOUNCE = 3, SETUP_MA230_BOUNCE = 4, SETUP_MA500_TOUCH = 5, SETUP_FIB_BREAK = 6, SETUP_FIB_RECLAIM = 7, SETUP_FIB_REJECT = 8, SETUP_MAGNET_WALK = 9, SETUP_STAIRCASE_ADV = 10, SETUP_CTRL_PULLBACK = 11, SETUP_TF_RESET = 12, SETUP_MFIB_LADDER = 13, SETUP_MFIB_PRESS = 14, SETUP_MEAN_REV = 15, SETUP_RANGE_ENGINE = 16 }; //================ GLOBALS ==================// int Stoch_Handle, ATR_Handle; double Stoch_K_Current = 0; double Stoch_K_Previous = 0; double Current_ATR = 0; double PriceLevels[7]; int MA_Handles[10]; double MA_Current[10]; double MA_Previous[10]; double MFIB_High, MFIB_Low; double MFIB_Level_236, MFIB_Level_382, MFIB_Level_050; double MFIB_Level_618, MFIB_Level_786; BIAS_STATE Current_Bias = BIAS_NEUTRAL; BIAS_STATE Previous_Bias = BIAS_NEUTRAL; int Bias_Confirmation_Count = 0; bool Price_Above_500 = false; struct Position { ulong ticket; double entry; double original_lot; bool is_buy; bool partial_tp_hit; bool be_set; bool trailing_active; SETUP_TYPE setup_type; string setup_name; }; Position OpenPositions[]; int TodayTrades = 0; int BuyTrades = 0; int SellTrades = 0; int ClosedByBias = 0; // Tracking per setup int SetupCount[17]; datetime LastEntryTime[17]; //+------------------------------------------------------------------+ int OnInit() { Print("========================================"); Print("BIAS FILTERED MODE v3.3"); Print("MA7 + MFIB + STOCH DIRECTIONAL BIAS"); Print("CLOSES OPPOSING TRADES ON BIAS FLIP"); Print("========================================"); Trade.SetExpertMagicNumber(MagicNumber); Trade.SetDeviationInPoints(50); Trade.SetTypeFilling(ORDER_FILLING_FOK); Stoch_Handle = iStochastic(_Symbol, PERIOD_CURRENT, Stoch_K_Period, Stoch_D_Period, Stoch_Slowing, MODE_SMA, STO_LOWHIGH); ATR_Handle = iATR(_Symbol, PERIOD_CURRENT, 14); int periods[10] = {MA_1, MA_2, MA_3, MA_4, MA_5, MA_6, MA_7, MA_8, MA_9, MA_10}; for(int i=0; i<10; i++) { MA_Handles[i] = iMA(_Symbol, PERIOD_CURRENT, periods[i], 0, MODE_EMA, PRICE_CLOSE); } ArrayInitialize(SetupCount, 0); ArrayInitialize(LastEntryTime, 0); CalculateLevels(); if(Show_Levels) DrawLevels(); Print("Bias Filter: ", Use_Bias_Filter ? "ON" : "OFF"); Print("Close Opposing: ", Close_Opposing_On_Flip ? "ON" : "OFF"); Print("300 Rule Active"); return INIT_SUCCEEDED; } //+------------------------------------------------------------------+ void OnDeinit(const int reason) { for(int i=0; i<10; i++) if(MA_Handles[i] != INVALID_HANDLE) IndicatorRelease(MA_Handles[i]); if(Stoch_Handle != INVALID_HANDLE) IndicatorRelease(Stoch_Handle); if(ATR_Handle != INVALID_HANDLE) IndicatorRelease(ATR_Handle); ObjectsDeleteAll(0, "Level_"); ObjectsDeleteAll(0, "Arrow_"); ObjectsDeleteAll(0, "BiasLabel"); Print("Buys:", BuyTrades, " | Sells:", SellTrades, " | Closed by Bias:", ClosedByBias); } //+------------------------------------------------------------------+ void CalculateLevels() { double high = iHigh(_Symbol, PERIOD_CURRENT, 0); double low = iLow(_Symbol, PERIOD_CURRENT, 0); for(int i=1; i<=Lookback_Bars; i++) { double h = iHigh(_Symbol, PERIOD_CURRENT, i); double l = iLow(_Symbol, PERIOD_CURRENT, i); if(h > high) high = h; if(l < low) low = l; } double range = high - low; PriceLevels[0] = low; PriceLevels[1] = low + range * 0.236; PriceLevels[2] = low + range * 0.382; PriceLevels[3] = low + range * 0.5; PriceLevels[4] = low + range * 0.618; PriceLevels[5] = low + range * 0.786; PriceLevels[6] = high; MFIB_High = high; MFIB_Low = low; MFIB_Level_236 = low + range * 0.236; MFIB_Level_382 = low + range * 0.382; MFIB_Level_050 = low + range * 0.5; MFIB_Level_618 = low + range * 0.618; MFIB_Level_786 = low + range * 0.786; } void DrawLevels() { ObjectsDeleteAll(0, "Level_"); color level_colors[7] = {clrRed, clrOrange, clrYellow, clrLime, clrCyan, clrBlue, clrMagenta}; for(int i=0; i<7; i++) { string name = "Level_" + IntegerToString(i); ObjectCreate(0, name, OBJ_HLINE, 0, 0, PriceLevels[i]); ObjectSetInteger(0, name, OBJPROP_COLOR, level_colors[i]); ObjectSetInteger(0, name, OBJPROP_STYLE, STYLE_SOLID); ObjectSetInteger(0, name, OBJPROP_WIDTH, 2); } } //+------------------------------------------------------------------+ void DetermineBias() { // MA7 Heartbeat Direction bool ma7_above_50 = MA_Current[0] > MA_Current[3]; bool ma7_above_140 = MA_Current[0] > MA_Current[4]; bool ma7_below_50 = MA_Current[0] < MA_Current[3]; bool ma7_below_140 = MA_Current[0] < MA_Current[4]; // MFIB Position double current = SymbolInfoDouble(_Symbol, SYMBOL_BID); bool above_mfib_50 = current > MFIB_Level_050; bool above_mfib_618 = current > MFIB_Level_618; bool below_mfib_50 = current < MFIB_Level_050; bool below_mfib_382 = current < MFIB_Level_382; // Stochastic Momentum bool stoch_bullish = Stoch_K_Current > 50; bool stoch_bearish = Stoch_K_Current < 50; bool stoch_strong_bull = Stoch_K_Current > 70; bool stoch_strong_bear = Stoch_K_Current < 30; // Price Position Price_Above_500 = current > MA_Current[6]; // Combine signals for bias int bull_signals = 0; int bear_signals = 0; if(ma7_above_50) bull_signals++; if(ma7_above_140) bull_signals++; if(above_mfib_50) bull_signals++; if(stoch_bullish) bull_signals++; if(Price_Above_500) bull_signals++; if(ma7_below_50) bear_signals++; if(ma7_below_140) bear_signals++; if(below_mfib_50) bear_signals++; if(stoch_bearish) bear_signals++; if(!Price_Above_500) bear_signals++; // Determine bias BIAS_STATE new_bias = BIAS_NEUTRAL; if(bull_signals >= 4 && above_mfib_618) new_bias = BIAS_STRONG_BULL; else if(bull_signals >= 3) new_bias = BIAS_BULL; else if(bear_signals >= 4 && below_mfib_382) new_bias = BIAS_STRONG_BEAR; else if(bear_signals >= 3) new_bias = BIAS_BEAR; else new_bias = BIAS_NEUTRAL; // Confirm bias change if(new_bias != Current_Bias) { if(new_bias == Previous_Bias) { Bias_Confirmation_Count++; if(Bias_Confirmation_Count >= Bias_Flip_Bars) { BIAS_STATE old_bias = Current_Bias; Current_Bias = new_bias; Bias_Confirmation_Count = 0; Print(">>> BIAS FLIP: ", EnumToString(old_bias), " → ", EnumToString(Current_Bias)); // Close opposing trades if(Close_Opposing_On_Flip) CloseOpposingTrades(); } } else { Previous_Bias = new_bias; Bias_Confirmation_Count = 1; } } else { Bias_Confirmation_Count = 0; } // Update label UpdateBiasLabel(); } //+------------------------------------------------------------------+ void UpdateBiasLabel() { ObjectDelete(0, "BiasLabel"); ObjectCreate(0, "BiasLabel", OBJ_LABEL, 0, 0, 0); ObjectSetInteger(0, "BiasLabel", OBJPROP_CORNER, CORNER_LEFT_UPPER); ObjectSetInteger(0, "BiasLabel", OBJPROP_XDISTANCE, 10); ObjectSetInteger(0, "BiasLabel", OBJPROP_YDISTANCE, 30); string text = ""; color bias_color = clrYellow; switch(Current_Bias) { case BIAS_STRONG_BULL: text = "BIAS: STRONG BULL ↑↑"; bias_color = clrLime; break; case BIAS_BULL: text = "BIAS: BULLISH ↑"; bias_color = clrGreenYellow; break; case BIAS_NEUTRAL: text = "BIAS: NEUTRAL ↔"; bias_color = clrYellow; break; case BIAS_BEAR: text = "BIAS: BEARISH ↓"; bias_color = clrOrange; break; case BIAS_STRONG_BEAR: text = "BIAS: STRONG BEAR ↓↓"; bias_color = clrRed; break; } ObjectSetString(0, "BiasLabel", OBJPROP_TEXT, text); ObjectSetInteger(0, "BiasLabel", OBJPROP_COLOR, bias_color); ObjectSetInteger(0, "BiasLabel", OBJPROP_FONTSIZE, 12); } //+------------------------------------------------------------------+ void CloseOpposingTrades() { for(int i=PositionsTotal()-1; i>=0; i--) { if(PositionGetTicket(i) == 0) continue; if(PositionGetString(POSITION_SYMBOL) != _Symbol) continue; if(PositionGetInteger(POSITION_MAGIC) != MagicNumber) continue; bool is_buy = PositionGetInteger(POSITION_TYPE) == POSITION_TYPE_BUY; bool should_close = false; // Close longs in bearish bias if(is_buy && (Current_Bias == BIAS_BEAR || Current_Bias == BIAS_STRONG_BEAR)) should_close = true; // Close shorts in bullish bias if(!is_buy && (Current_Bias == BIAS_BULL || Current_Bias == BIAS_STRONG_BULL)) should_close = true; if(should_close) { ulong ticket = PositionGetTicket(i); if(Trade.PositionClose(ticket)) { ClosedByBias++; Print("✂ BIAS CLOSE: ", is_buy ? "BUY" : "SELL", " @ ", DoubleToString(PositionGetDouble(POSITION_PRICE_CURRENT), _Digits)); } } } } //+------------------------------------------------------------------+ void UpdateIndicators() { for(int i=0; i<10; i++) { double curr[1], prev[1]; if(CopyBuffer(MA_Handles[i], 0, 0, 1, curr) > 0) MA_Current[i] = curr[0]; if(CopyBuffer(MA_Handles[i], 0, 1, 1, prev) > 0) MA_Previous[i] = prev[0]; } double k_curr[1], k_prev[1]; if(CopyBuffer(Stoch_Handle, MAIN_LINE, 0, 1, k_curr) > 0) Stoch_K_Current = k_curr[0]; if(CopyBuffer(Stoch_Handle, MAIN_LINE, 1, 1, k_prev) > 0) Stoch_K_Previous = k_prev[0]; double atr[1]; if(CopyBuffer(ATR_Handle, 0, 0, 1, atr) > 0) Current_ATR = atr[0]; } //+------------------------------------------------------------------+ int CountSetupTrades(SETUP_TYPE setup) { int count = 0; for(int i=0; i= Max_Trades_Per_Setup) return; if(PositionsTotal() >= Max_Total_Trades) return; datetime now = TimeCurrent(); if(now - LastEntryTime[setup_type] < 1) return; LastEntryTime[setup_type] = now; double lot = GetLotSize(); if(lot < SymbolInfoDouble(_Symbol, SYMBOL_VOLUME_MIN)) return; double sl = buy ? price - Initial_SL_Points * _Point : price + Initial_SL_Points * _Point; double tp = buy ? price + TP_Points * _Point : price - TP_Points * _Point; string bias_text = EnumToString(Current_Bias); string comment = setup_name + "|" + bias_text; bool result = false; if(buy) result = Trade.Buy(lot, _Symbol, 0, sl, tp, comment); else result = Trade.Sell(lot, _Symbol, 0, sl, tp, comment); if(result) { TodayTrades++; if(buy) BuyTrades++; else SellTrades++; SetupCount[setup_type]++; ulong ticket = Trade.ResultOrder(); int size = ArraySize(OpenPositions); ArrayResize(OpenPositions, size+1); OpenPositions[size].ticket = ticket; OpenPositions[size].entry = price; OpenPositions[size].original_lot = lot; OpenPositions[size].is_buy = buy; OpenPositions[size].partial_tp_hit = false; OpenPositions[size].be_set = false; OpenPositions[size].trailing_active = false; OpenPositions[size].setup_type = setup_type; OpenPositions[size].setup_name = setup_name; Print("✓ ", setup_name, " ", buy ? "BUY" : "SELL", " [", CountSetupTrades(setup_type), "/", Max_Trades_Per_Setup, "] | B:", BuyTrades, " S:", SellTrades); } } //+------------------------------------------------------------------+ void ManagePositions() { for(int i=PositionsTotal()-1; i>=0; i--) { ulong ticket = PositionGetTicket(i); if(ticket == 0) continue; if(PositionGetString(POSITION_SYMBOL) != _Symbol) continue; if(PositionGetInteger(POSITION_MAGIC) != MagicNumber) continue; int idx = -1; for(int j=0; j= Partial_TP_Points) { double current_lot = PositionGetDouble(POSITION_VOLUME); double close_size = NormalizeDouble(OpenPositions[idx].original_lot * Partial_TP_Percent / 100.0, 2); if(close_size > 0 && close_size <= current_lot) { if(Trade.PositionClosePartial(ticket, close_size)) { OpenPositions[idx].partial_tp_hit = true; } } } if(!OpenPositions[idx].be_set && profit_points >= BreakEven_Points) { if((is_buy && current_sl < entry) || (!is_buy && current_sl > entry)) { if(Trade.PositionModify(ticket, entry, current_tp)) { OpenPositions[idx].be_set = true; } } } if(profit_points >= BreakEven_Points + 100) { OpenPositions[idx].trailing_active = true; double newSL = 0; bool should_modify = false; if(is_buy) { newSL = current - Trailing_Distance_Points * _Point; if(newSL > current_sl + 30 * _Point) should_modify = true; } else { newSL = current + Trailing_Distance_Points * _Point; if(newSL < current_sl - 30 * _Point) should_modify = true; } if(should_modify) Trade.PositionModify(ticket, newSL, current_tp); } } } //+------------------------------------------------------------------+ void OnTick() { UpdateIndicators(); DetermineBias(); ManagePositions(); static int tick_count = 0; tick_count++; if(tick_count >= 100) { CalculateLevels(); tick_count = 0; } double bid = SymbolInfoDouble(_Symbol, SYMBOL_BID); double ask = SymbolInfoDouble(_Symbol, SYMBOL_ASK); double current = (bid + ask) / 2; double previous = iClose(_Symbol, PERIOD_CURRENT, 1); double buffer = MA_Touch_Buffer * _Point; //================================================================= // ALL SETUPS WITH BIAS FILTERING //================================================================= // SETUP 1: MA14 CROSS int ma14_crosses = 0; for(int i=0; i<10; i++) if(i != 1 && MA_Current[1] > MA_Current[i]) ma14_crosses++; if(ma14_crosses >= 2) OpenTrade(true, ask, "MA14-CROSS↑", SETUP_MA14_CROSS); ma14_crosses = 0; for(int i=0; i<10; i++) if(i != 1 && MA_Current[1] < MA_Current[i]) ma14_crosses++; if(ma14_crosses >= 2) OpenTrade(false, bid, "MA14-CROSS↓", SETUP_MA14_CROSS); // SETUP 2-5: MA BOUNCES if(MathAbs(current - MA_Current[3]) <= buffer) { OpenTrade(true, ask, "MA50-BOUNCE↑", SETUP_MA50_BOUNCE); OpenTrade(false, bid, "MA50-BOUNCE↓", SETUP_MA50_BOUNCE); } if(MathAbs(current - MA_Current[4]) <= buffer) { OpenTrade(true, ask, "MA140-BOUNCE↑", SETUP_MA140_BOUNCE); OpenTrade(false, bid, "MA140-BOUNCE↓", SETUP_MA140_BOUNCE); } if(MathAbs(current - MA_Current[5]) <= buffer) { OpenTrade(true, ask, "MA230-BOUNCE↑", SETUP_MA230_BOUNCE); OpenTrade(false, bid, "MA230-BOUNCE↓", SETUP_MA230_BOUNCE); } if(MathAbs(current - MA_Current[6]) <= buffer) { OpenTrade(true, ask, "MA500-TOUCH↑", SETUP_MA500_TOUCH); OpenTrade(false, bid, "MA500-TOUCH↓", SETUP_MA500_TOUCH); } // SETUP 6-8: FIB TRADING for(int i=1; i<6; i++) { if(MathAbs(current - PriceLevels[i]) <= buffer) { if(previous < PriceLevels[i]) OpenTrade(true, ask, "FIB-BREAK↑", SETUP_FIB_BREAK); if(previous > PriceLevels[i]) OpenTrade(false, bid, "FIB-BREAK↓", SETUP_FIB_BREAK); } } // SETUP 9: MAGNET WALK bool hugging = (MathAbs(current - MA_Current[2]) / Current_ATR < 0.7); if(hugging && MA_Current[0] > MA_Current[3]) OpenTrade(true, ask, "MAGNET-WALK↑", SETUP_MAGNET_WALK); if(hugging && MA_Current[0] < MA_Current[3]) OpenTrade(false, bid, "MAGNET-WALK↓", SETUP_MAGNET_WALK); // SETUP 10: STAIRCASE if(MA_Current[1] > MA_Previous[1] && MA_Current[1] > MA_Current[3]) OpenTrade(true, ask, "STAIRCASE↑", SETUP_STAIRCASE_ADV); if(MA_Current[1] < MA_Previous[1] && MA_Current[1] < MA_Current[3]) OpenTrade(false, bid, "STAIRCASE↓", SETUP_STAIRCASE_ADV); // SETUP 11: CONTROLLED PULLBACK bool near_ma = MathAbs(current - MA_Current[3]) / Current_ATR < 1.5; bool stoch_reset_bull = Stoch_K_Previous > 55 && Stoch_K_Current < 50; bool stoch_reset_bear = Stoch_K_Previous < 45 && Stoch_K_Current > 50; if(near_ma && stoch_reset_bull) OpenTrade(true, ask, "CTRL-PULLBACK↑", SETUP_CTRL_PULLBACK); if(near_ma && stoch_reset_bear) OpenTrade(false, bid, "CTRL-PULLBACK↓", SETUP_CTRL_PULLBACK); // SETUP 12: TIMEFRAME RESET if(Stoch_K_Current < 35 && MA_Current[0] > MA_Current[6]) OpenTrade(true, ask, "TF-RESET↑", SETUP_TF_RESET); if(Stoch_K_Current > 65 && MA_Current[0] < MA_Current[6]) OpenTrade(false, bid, "TF-RESET↓", SETUP_TF_RESET); // SETUP 13: MFIB LADDER if(MathAbs(current - MFIB_Level_618) <= buffer) { if(previous <= MFIB_Level_618) OpenTrade(true, ask, "MFIB-LADDER618↑", SETUP_MFIB_LADDER); if(previous >= MFIB_Level_618) OpenTrade(false, bid, "MFIB-LADDER618↓", SETUP_MFIB_LADDER); } // SETUP 14: MFIB PRESS bool near_mfib = MathAbs(current - MFIB_Level_050) / Current_ATR < 1.2; if(near_mfib && MA_Current[1] > MA_Current[3]) OpenTrade(true, ask, "MFIB-PRESS↑", SETUP_MFIB_PRESS); if(near_mfib && MA_Current[1] < MA_Current[3]) OpenTrade(false, bid, "MFIB-PRESS↓", SETUP_MFIB_PRESS); // SETUP 15: MEAN REVERSION bool near_230 = MathAbs(current - MA_Current[5]) / Current_ATR < 1.0; if(near_230 && Stoch_K_Current < Stoch_Oversold) OpenTrade(true, ask, "MEAN-REV-BUY", SETUP_MEAN_REV); if(near_230 && Stoch_K_Current > Stoch_Overbought) OpenTrade(false, bid, "MEAN-REV-SELL", SETUP_MEAN_REV); // SETUP 16: RANGE ENGINE if(MathAbs(current - PriceLevels[1]) < buffer && Stoch_K_Current < 35) OpenTrade(true, ask, "RANGE-BUY", SETUP_RANGE_ENGINE); if(MathAbs(current - PriceLevels[5]) < buffer && Stoch_K_Current > 65) OpenTrade(false, bid, "RANGE-SELL", SETUP_RANGE_ENGINE); } //+------------------------------------------------------------------+