One Cancels Other Manager
A breakout setup with a buy stop above the market and a sell stop below needs something watching both legs, because neither platform has a native one-cancels-other order type. Without it, price can spike through one leg, retrace, and trigger the other too - leaving the trader with two opposite positions instead of the single directional trade the setup was meant to be. Each group's ticket list is genuinely ragged - a two-leg breakout, a three- way straddle, whatever the caller assembles - so both versions of this header use a struct-of-dynamic-arrays: SOcoGroup owns its own tickets[] array, and many independent groups of different sizes can exist side by side. Detecting a trigger is the trap most naive versions of this get wrong, and it is solved completely differently on the two platforms. MQL4's pending pool re-indexes on every change, so scanning it by position is unreliable; this header instead re-selects each member's own ticket by SELECT_BY_TICKET on every update, because a triggered MQL4 pending order keeps its ticket number and simply changes OrderType() to OP_BUY or OP_SELL. MQL5 has no such guarantee at all - a filled pending order leaves the live order pool entirely and its ticket only exists in history from that point on, while the resulting position is a completely separate object with its own, different ticket. The MQL5 header instead watches OrderSelect(ticket) for "still resting," and once that stops finding it, resolves what happened by reading HistoryOrderGetInteger(ticket, ORDER_POSITION_ID) off the now-historical order record - a non-zero id means it triggered, a zero id (or the ticket missing from history too) means it was cancelled, expired or rejected instead. The header is self-contained. No dependencies, no DLLs - it links tickets you already sent (via OrderSend on MQL4, or CTrade/OrderSend on MQL5), it does not place orders itself. Notes and limitations - A group only cancels its OTHER pending members when one member triggers. It never touches the resulting market position - that is a separate concern (stop management, trailing) outside this header's job. On MQL5, Oco_TriggeredPositionId() gives you the ticket to hand to that separate concern. - A member ticket that disappears without triggering (expired, or deleted by hand outside this header) is treated the same as a deliberate manual cancel: the group is not resolved by it and other members are left alone, since the header cannot distinguish "the trader meant to cancel this leg" from "the broker expired it" - and assuming a trigger in that case would be the more dangerous guess. On MQL5 this is read from HistoryOrderGetInteger(ticket, ORDER_POSITION_ID) being zero (or the ticket not appearing in history at all yet). - Group state lives in module-level arrays for the lifetime of the chart or script. It is not persisted to disk, so a terminal restart loses in-flight group bookkeeping even though any already-triggered positions remain open exactly as they are on the trade server. - This header links tickets, it does not send them. Volume normalisation, stop-level validation and retry-on-requote for the initial order-placement calls are the caller's responsibility (or reuse a dedicated order-sending library alongside this one). - MQL5's Oco_Update() calls HistorySelect(0, TimeCurrent()) on every poll to cover full history, not a narrow recent window - a member placed long before a given Update() call still needs to resolve correctly the first time it is checked.
Script · MT4 · v1.0 · Free
About One Cancels Other Manager
One Cancels Other Manager is an expert advisor (trading robot) for MetaTrader 4. It places pending buy/sell stop or limit orders. It has 2 settings, such as Place real order and Distance points. MQL source code included.
Files in the download: OcoOrderManager.mqh, OcoOrderManager.txt, OcoOrderManagerDemo.mq4.
Trading robots can lose money. Check every setting and test on a demo account before using real funds.
Settings
| Setting | Default | What it does |
|---|---|---|
| Place real order | false | WARNING: true opens a real two-leg pending straddle on this symbol |
| Distance points | 500 | Distance from market used for the safe demo pending prices |
How to install
- Download the ZIP from your PolyMaria library and unzip it.
- In MetaTrader 4 open File → Open Data Folder, then go to MQL4 → Experts.
- Copy the .mq4 file(s) there. Put any .mqh files in MQL4 → Include.
- Open the .mq4 file in MetaEditor and press Compile (F7) if MetaTrader does not show it.
- Drag the expert advisor from the Navigator onto a chart, check the settings, allow Algo/Auto Trading and press OK.
- Test it first on a demo account or in the Strategy Tester.
Tags: Breakout · Pending Orders · MT4 Script · MQL4 Source Code