Grafiken in der Bibliothek DoEasy (Teil 83): Die Klasse des abstrakten grafischen Standardobjekts
Inhalt
- Konzept
- Verbesserung der Klassenbibliothek
- Die Klasse des abstrakten Grafikobjekts
- Test
- Was kommt als Nächstes?
Konzept
Um die Kollektionsklasse für grafische Objekte, die ich im vorigen Artikel implementiert habe, weiter zu verbessern, benötige ich die Objektklassen aller grafischen Standardobjekte, die im Terminal vorhanden sind. Wenn ich alle diese Objekte erstellt habe, verfüge ich über die Werkzeuge zur Handhabung aller grafischen Objekte (Standard- und nutzerdefinierte), die auf der Klasse CCanvas basieren. Sie werden alle in der Kollektionsliste der grafischen Objekte zu finden sein.
Da die Bibliothek in der Lage sein soll, manuell erstellte grafische Objekte zu verwalten, benötige ich die Klassen von Objekten, die manuell erstellte grafische Standardobjekte beschreiben. Ein solches Objekt soll an das manuell erstellte grafische Objekt und die Methoden zur Verwaltung seiner Eigenschaften gebunden werden. Um ein solches grafisches Objekt zu verwalten, sollte ein Bibliotheksbenutzer manuell die Notwendigkeit einer solchen Verwaltung angeben.
Dies kann zum Beispiel über das Kontextmenü geschehen, das bei einer bestimmten Bedingung aufgerufen wird. Das bedeutet, dass wir ein grafisches Panel benötigen, das die Auswahl der verfügbaren Aktionen mit einem grafischen Objekt ermöglicht. Solche Panels können mit den CCanvas-basierten Klassen und ihren Objekten erstellt werden, die ich vor einigen Artikeln begonnen habe zu erstellen. Ich habe vor, darauf zurückzukommen, sobald die grafische Objektsammlung und die entsprechenden Klassen für grafische Standardobjekte erstellt sind.
Die Struktur aller grafischen Standardobjekte bleibt die gleiche wie die aller Bibliotheksobjekte. Es gibt eine gemeinsame abstrakte grafische Objektklasse, die grundlegende Eigenschaften aufweist, die allen grafischen Objekten eigen sind. Die Klassen, die jedes einzelne grafische Standardobjekt beschreiben, werden von dieser Klasse geerbt. Diese Klassen werden verwendet, um die Objekteigenschaften zu spezifizieren.
Hier werde ich die abstrakte grafische Objektklasse erstellen und die Methoden zur Behandlung der Eigenschaften hinzufügen, die allen grafischen Objekten eigen sind — dies sind alle Eigenschaften grafischer Objekte, die mit den Funktionen ObjectGetInteger(), ObjectGetDouble() und ObjectGetString() erhalten werden können. Bei der Erstellung von abgeleiteten Objektklassen aus dem abstrakten grafischen Objekt werden die Methoden, die nur in einem Nachfolgeobjekt enthalten sind, das ein bestimmtes grafisches Objekt beschreibt, aber im Basisobjekt implementiert sind, vom Basisobjekt in das Nachfolgeobjekt verschoben, so dass Objekte ohne diese Eigenschaften keinen Zugriff auf die Methoden haben.
Betrachten wir zur Verdeutlichung das folgende Beispiel:
- Das Terminal verfügt über das grafische Symbolobjekt Pfeil. Das Objekt verfügt über die Eigenschaft Pfeilcode, aber nicht über Strahl rechts;
- Das Terminal verfügt über das grafische Objekt Trendlinie. Das Objekt verfügt über die Eigenschaft Strahl rechts, aber nicht über Pfeil-Codes.
Ich werde diese Eigenschaften und Bearbeitungsmethoden in der abstrakten grafischen Objektklasse festlegen. Diese Methoden werden von jedem Objekt verfügbar sein, das vom Basisobjekt — dem abstrakten grafischen Objekt — geerbt wird.
Als Nächstes werde ich abhängige Objekte erstellen. In diesem Fall sind dies das Pfeilsymbolobjekt und das grafische Trendlinienobjekt. Jedes von ihnen soll die Methoden erhalten, die nur die ihnen eigenen Eigenschaften behandeln:
- Die Methoden zur Angabe eines Pfeilcodes werden in das Objekt Pfeilsymbol verschoben;
- die Methoden zur Angabe der Eigenschaft Strahl rechts (Strahl links) werden in das grafische Objekt Trendlinie verlagert.
Wenn wir uns auf jedes dieser nachgeordneten Objekte beziehen, haben wir nur Zugriff auf seine spezifischen Eigenschaften, deren Bearbeitungsmethoden nur in diesen Objekten festgelegt sind, zusammen mit den Methoden zur Bearbeitung der Eigenschaften, die allen Objekten gemeinsam sind, die in jedem grafischen Objekt enthalten und in der abstrakten grafischen Objektklasse festgelegt sind.
Grafische Objekte haben mehrere Eigenschaften. Daher muss ich vor der eigentlichen Erstellung der Klasse des abstrakten grafischen Objekts eine Menge Vorarbeit leisten. Diese Arbeit umfasst das Setzen der Eigenschaften in den Bibliotheksaufzählungen, das Schreiben von Beschreibungen für jede grafische Objekteigenschaft und das Erstellen von Funktionen, die Beschreibungen einiger grafischer Objekteigenschaften zurückgeben.
Verbesserung der Klassenbibliothek
Die Liste der Bibliotheksobjekttypen, die ich im vorherigen Artikel erstellt habe, enthält die Standardtypen für grafische Objekte. Wir benötigen jedoch noch einen weiteren Typ für ein abstraktes grafisches Objekt. Wir tragen die Konstante in die Enumeration der Bibliotheksobjekttypen in \MQL5\Include\DoEasy\Defines.mqh ein. Die Berechnung der nachfolgenden Objekttypkonstanten wird ausgehend von dem neuen Konstantenwert gestartet:
//+------------------------------------------------------------------+ //| List of library object types | //+------------------------------------------------------------------+ enum ENUM_OBJECT_DE_TYPE { //--- Graphics OBJECT_DE_TYPE_GBASE = COLLECTION_ID_LIST_END+1, // "Base object of all library graphical objects" object type OBJECT_DE_TYPE_GELEMENT, // "Graphical element" object type OBJECT_DE_TYPE_GFORM, // Form object type OBJECT_DE_TYPE_GSHADOW, // Shadow object type //--- Animation OBJECT_DE_TYPE_GFRAME, // "Single animation frame" object type OBJECT_DE_TYPE_GFRAME_TEXT, // "Single text animation frame" object type OBJECT_DE_TYPE_GFRAME_QUAD, // "Single rectangular animation frame" object type OBJECT_DE_TYPE_GFRAME_GEOMETRY, // "Single geometric animation frame" object type OBJECT_DE_TYPE_GANIMATIONS, // "Animations" object type //--- Managing graphical objects OBJECT_DE_TYPE_GELEMENT_CONTROL, // "Managing graphical objects" object type //--- Standard graphical objects OBJECT_DE_TYPE_GSTD_OBJ, // "Standard graphical object" object type OBJECT_DE_TYPE_GSTD_VLINE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_VLINE, // "Vertical line" object type OBJECT_DE_TYPE_GSTD_HLINE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_HLINE, // "Horizontal line" object type OBJECT_DE_TYPE_GSTD_TREND = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_TREND, // "Trend line" object type OBJECT_DE_TYPE_GSTD_TRENDBYANGLE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_TRENDBYANGLE, // "Trend line by angle" object type OBJECT_DE_TYPE_GSTD_CYCLES = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_CYCLES, // "Cyclic lines" object type OBJECT_DE_TYPE_GSTD_ARROWED_LINE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROWED_LINE, // "Arrowed line" object type OBJECT_DE_TYPE_GSTD_CHANNEL = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_CHANNEL, // "Equidistant channel" object type OBJECT_DE_TYPE_GSTD_STDDEVCHANNEL = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_STDDEVCHANNEL, // "Standard deviation channel" object type OBJECT_DE_TYPE_GSTD_REGRESSION = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_REGRESSION, // "Linear regression channel" object type OBJECT_DE_TYPE_GSTD_PITCHFORK = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_PITCHFORK, // "Andrews' pitchfork" object type OBJECT_DE_TYPE_GSTD_GANNLINE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_GANNLINE, // "Gann line" object type OBJECT_DE_TYPE_GSTD_GANNFAN = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_GANNFAN, // "Gann fan" object type OBJECT_DE_TYPE_GSTD_GANNGRID = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_GANNGRID, // "Gann grid" object type OBJECT_DE_TYPE_GSTD_FIBO = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_FIBO, // "Fibo levels" object type OBJECT_DE_TYPE_GSTD_FIBOTIMES = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_FIBOTIMES, // "Fibo time zones" object type OBJECT_DE_TYPE_GSTD_FIBOFAN = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_FIBOFAN, // "Fibo fan" object type OBJECT_DE_TYPE_GSTD_FIBOARC = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_FIBOARC, // "Fibo arcs" object type OBJECT_DE_TYPE_GSTD_FIBOCHANNEL = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_FIBOCHANNEL, // "Fibo channel" object type OBJECT_DE_TYPE_GSTD_EXPANSION = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_EXPANSION, // "Fibo expansion" object type OBJECT_DE_TYPE_GSTD_ELLIOTWAVE5 = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ELLIOTWAVE5, // "Elliott 5 waves" object type OBJECT_DE_TYPE_GSTD_ELLIOTWAVE3 = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ELLIOTWAVE3, // "Elliott 3 waves" object type OBJECT_DE_TYPE_GSTD_RECTANGLE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_RECTANGLE, // "Rectangle" object type OBJECT_DE_TYPE_GSTD_TRIANGLE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_TRIANGLE, // "Triangle" object type OBJECT_DE_TYPE_GSTD_ELLIPSE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ELLIPSE, // "Ellipse" object type OBJECT_DE_TYPE_GSTD_ARROW_THUMB_UP = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_THUMB_UP, // "Thumb up" object type OBJECT_DE_TYPE_GSTD_ARROW_THUMB_DOWN = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_THUMB_DOWN, // "Thumb down" object type OBJECT_DE_TYPE_GSTD_ARROW_UP = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_UP, // "Arrow up" object type OBJECT_DE_TYPE_GSTD_ARROW_DOWN = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_DOWN, // "Arrow down" object type OBJECT_DE_TYPE_GSTD_ARROW_STOP = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_STOP, // "Stop sign" object type OBJECT_DE_TYPE_GSTD_ARROW_CHECK = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_CHECK, // "Check mark" object type OBJECT_DE_TYPE_GSTD_ARROW_LEFT_PRICE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_LEFT_PRICE, // "Left price label" object type OBJECT_DE_TYPE_GSTD_ARROW_RIGHT_PRICE = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_RIGHT_PRICE,// "Right price label" object type OBJECT_DE_TYPE_GSTD_ARROW_BUY = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_BUY, // "Buy sign" object type OBJECT_DE_TYPE_GSTD_ARROW_SELL = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW_SELL, // "Sell sign" object type OBJECT_DE_TYPE_GSTD_ARROW = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_ARROW, // "Arrow" object type OBJECT_DE_TYPE_GSTD_TEXT = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_TEXT, // "Text" object type OBJECT_DE_TYPE_GSTD_LABEL = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_LABEL, // "Text label" object type OBJECT_DE_TYPE_GSTD_BUTTON = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_BUTTON, // "Button" object type OBJECT_DE_TYPE_GSTD_CHART = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_CHART, // "Chart" object type OBJECT_DE_TYPE_GSTD_BITMAP = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_BITMAP, // "Bitmap" object type OBJECT_DE_TYPE_GSTD_BITMAP_LABEL = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_BITMAP_LABEL, // "Bitmap label" object type OBJECT_DE_TYPE_GSTD_EDIT = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_EDIT, // "Input field" object type OBJECT_DE_TYPE_GSTD_EVENT = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_EVENT, // "Event object which corresponds to an event in Economic Calendar" object type OBJECT_DE_TYPE_GSTD_RECTANGLE_LABEL = OBJECT_DE_TYPE_GSTD_OBJ+1+OBJ_RECTANGLE_LABEL, // "Rectangle Label object used to create and design the custom graphical interface" object type //--- Objects OBJECT_DE_TYPE_BASE = OBJECT_DE_TYPE_GSTD_RECTANGLE_LABEL+1, // Base object for all library objects OBJECT_DE_TYPE_BASE_EXT, // Extended base object for all library objects // .......... The constants of other object types are skipped for brevity // .......... // .......... };
In der Enumeration der Zugehörigkeitsliste von grafischen Objekten ändern wir die Konstante GRAPH_OBJ_BELONG_TERMINAL, deren Name angibt, dass das grafische Objekt zum Terminal gehört. Lassen Sie uns die Konstante geeigneter gestalten: GRAPH_OBJ_BELONG_NO_PROGRAM, da das Objekt möglicherweise nicht zu dem von der Bibliothek kontrollierten Programm gehört, sondern zu einem anderen Programm als dem Terminal:
//+------------------------------------------------------------------+ //| List of graphical objects affiliations | //+------------------------------------------------------------------+ enum ENUM_GRAPH_OBJ_BELONG { GRAPH_OBJ_BELONG_PROGRAM, // Graphical object belongs to a program GRAPH_OBJ_BELONG_NO_PROGRAM, // Graphical object does not belong to a program }; //+------------------------------------------------------------------+
Fügen wir eine neuen Konstante zur Enumeration der grafischen Elementtypen hinzu:
//+------------------------------------------------------------------+ //| The list of graphical element types | //+------------------------------------------------------------------+ enum ENUM_GRAPH_ELEMENT_TYPE { GRAPH_ELEMENT_TYPE_STANDART, // Standard graphical object GRAPH_ELEMENT_TYPE_ELEMENT, // Element GRAPH_ELEMENT_TYPE_SHADOW_OBJ, // Shadow object GRAPH_ELEMENT_TYPE_FORM, // Form GRAPH_ELEMENT_TYPE_WINDOW, // Window }; //+------------------------------------------------------------------+
Da alle Objekte, die in einem Programm erstellte grafische Objekte beschreiben, in einer einzigen Liste gespeichert werden sollen, ermöglicht die Angabe des grafischen Elementtyps eine schnelle Auswahl der benötigten grafischen Elemente aus der gesamten Liste. Wenn wir also "Standardgrafikobjekt" als Filterbedingung für die Kollektionsliste wählen, erhalten wir die Liste, die nur aus Objekten besteht, die die erstellten Standardgrafikobjekte beschreiben.
Für ein Objekt der abstrakten Klasse der grafischen Standardobjekte müssen wir drei Enumerationen für alle Eigenschaften der grafischen Objekte erstellen — ganze Zahlen, reelle Zahlen und Text, die alle Eigenschaften der grafischen Objekte enthalten sollen, sowie die zusätzlichen, die für die Handhabung solcher Objekte notwendig sind:
//+------------------------------------------------------------------+ //| Integer properties of a standard graphical object | //+------------------------------------------------------------------+ enum ENUM_GRAPH_OBJ_PROP_INTEGER { //--- Additional properties GRAPH_OBJ_PROP_ID = 0, // Object ID GRAPH_OBJ_PROP_TYPE, // Graphical object type (ENUM_OBJECT) GRAPH_OBJ_PROP_ELEMENT_TYPE, // Graphical element type (ENUM_GRAPH_ELEMENT_TYPE) GRAPH_OBJ_PROP_BELONG, // Graphical object affiliation GRAPH_OBJ_PROP_CHART_ID, // Chart ID GRAPH_OBJ_PROP_WND_NUM, // Chart subwindow index GRAPH_OBJ_PROP_NUM, // Object index in the list //--- Common properties of all graphical objects GRAPH_OBJ_PROP_CREATETIME, // Object creation time GRAPH_OBJ_PROP_TIMEFRAMES, // Object visibility on timeframes GRAPH_OBJ_PROP_BACK, // Background object GRAPH_OBJ_PROP_ZORDER, // Priority of a graphical object for receiving the event of clicking on a chart GRAPH_OBJ_PROP_HIDDEN, // Disable displaying the name of a graphical object in the terminal object list GRAPH_OBJ_PROP_SELECTED, // Object selection GRAPH_OBJ_PROP_SELECTABLE, // Object availability //--- Properties belonging to different graphical objects GRAPH_OBJ_PROP_TIME, // Time coordinate GRAPH_OBJ_PROP_COLOR, // Color GRAPH_OBJ_PROP_STYLE, // Style GRAPH_OBJ_PROP_WIDTH, // Line width GRAPH_OBJ_PROP_FILL, // Object color filling GRAPH_OBJ_PROP_READONLY, // Ability to edit text in the Edit object GRAPH_OBJ_PROP_LEVELS, // Number of levels GRAPH_OBJ_PROP_LEVELCOLOR, // Level line color GRAPH_OBJ_PROP_LEVELSTYLE, // Level line style GRAPH_OBJ_PROP_LEVELWIDTH, // Level line width GRAPH_OBJ_PROP_ALIGN, // Horizontal text alignment in the Edit object (OBJ_EDIT) GRAPH_OBJ_PROP_FONTSIZE, // Font size GRAPH_OBJ_PROP_RAY_LEFT, // Ray goes to the left GRAPH_OBJ_PROP_RAY_RIGHT, // Ray goes to the right GRAPH_OBJ_PROP_RAY, // Vertical line goes through all windows of a chart GRAPH_OBJ_PROP_ELLIPSE, // Display the full ellipse of the Fibonacci Arc object GRAPH_OBJ_PROP_ARROWCODE, // Arrow code for the "Arrow" object GRAPH_OBJ_PROP_ANCHOR, // Position of the binding point of the graphical object GRAPH_OBJ_PROP_XDISTANCE, // Distance from the base corner along the X axis in pixels GRAPH_OBJ_PROP_YDISTANCE, // Distance from the base corner along the Y axis in pixels GRAPH_OBJ_PROP_DIRECTION, // Gann object trend GRAPH_OBJ_PROP_DEGREE, // Elliott wave marking level GRAPH_OBJ_PROP_DRAWLINES, // Display lines for Elliott wave marking GRAPH_OBJ_PROP_STATE, // Button state (pressed/released) GRAPH_OBJ_PROP_OBJ_CHART_ID, // Chart object ID (OBJ_CHART). GRAPH_OBJ_PROP_CHART_OBJ_PERIOD, // Chart object period GRAPH_OBJ_PROP_CHART_OBJ_DATE_SCALE, // Time scale display flag for the Chart object GRAPH_OBJ_PROP_CHART_OBJ_PRICE_SCALE, // Price scale display flag for the Chart object GRAPH_OBJ_PROP_CHART_OBJ_CHART_SCALE, // Chart object scale GRAPH_OBJ_PROP_XSIZE, // Object width along the X axis in pixels. GRAPH_OBJ_PROP_YSIZE, // Object height along the Y axis in pixels. GRAPH_OBJ_PROP_XOFFSET, // X coordinate of the upper-left corner of the visibility area. GRAPH_OBJ_PROP_YOFFSET, // Y coordinate of the upper-left corner of the visibility area. GRAPH_OBJ_PROP_BGCOLOR, // Background color for OBJ_EDIT, OBJ_BUTTON, OBJ_RECTANGLE_LABEL GRAPH_OBJ_PROP_CORNER, // Chart corner for binding a graphical object GRAPH_OBJ_PROP_BORDER_TYPE, // Border type for "Rectangle border" GRAPH_OBJ_PROP_BORDER_COLOR, // Border color for OBJ_EDIT and OBJ_BUTTON }; #define GRAPH_OBJ_PROP_INTEGER_TOTAL (51) // Total number of integer properties #define GRAPH_OBJ_PROP_INTEGER_SKIP (0) // Number of integer properties not used in sorting //+------------------------------------------------------------------+ //| Real properties of a standard graphical object | //+------------------------------------------------------------------+ enum ENUM_GRAPH_OBJ_PROP_DOUBLE { GRAPH_OBJ_PROP_PRICE = GRAPH_OBJ_PROP_INTEGER_TOTAL,// Price coordinate GRAPH_OBJ_PROP_LEVELVALUE, // Level value GRAPH_OBJ_PROP_SCALE, // Scale GRAPH_OBJ_PROP_ANGLE, // Angle GRAPH_OBJ_PROP_DEVIATION, // Deviation of the standard deviation channel }; #define GRAPH_OBJ_PROP_DOUBLE_TOTAL (5) // Total number of real properties #define GRAPH_OBJ_PROP_DOUBLE_SKIP (0) // Number of real properties not used in sorting //+------------------------------------------------------------------+ //| String properties of a standard graphical object | //+------------------------------------------------------------------+ enum ENUM_GRAPH_OBJ_PROP_STRING { GRAPH_OBJ_PROP_NAME = (GRAPH_OBJ_PROP_INTEGER_TOTAL+GRAPH_OBJ_PROP_DOUBLE_TOTAL), // Object name GRAPH_OBJ_PROP_TEXT, // Object description (text contained in the object) GRAPH_OBJ_PROP_TOOLTIP, // Tooltip text GRAPH_OBJ_PROP_LEVELTEXT, // Level description GRAPH_OBJ_PROP_FONT, // Font GRAPH_OBJ_PROP_BMPFILE, // BMP file name for the "Bitmap Level" object GRAPH_OBJ_PROP_CHART_OBJ_SYMBOL, // Symbol for the Chart object }; #define GRAPH_OBJ_PROP_STRING_TOTAL (7) // Total number of string properties //+------------------------------------------------------------------+
Wir kennen den Zweck solcher Enumerationen bereits, da alle Bibliotheksobjekte demselben Prinzip folgen.
Daher müssen wir auch die Enumeration möglicher Kriterien für die Sortierung von grafischen Objekten in die Kollektionsliste aufnehmen:
//+------------------------------------------------------------------+ //| Possible sorting criteria of graphical objects | //+------------------------------------------------------------------+ #define FIRST_GRAPH_OBJ_DBL_PROP (GRAPH_OBJ_PROP_INTEGER_TOTAL-GRAPH_OBJ_PROP_INTEGER_SKIP) #define FIRST_GRAPH_OBJ_STR_PROP (GRAPH_OBJ_PROP_INTEGER_TOTAL-GRAPH_OBJ_PROP_INTEGER_SKIP+GRAPH_OBJ_PROP_DOUBLE_TOTAL-GRAPH_OBJ_PROP_DOUBLE_SKIP) enum ENUM_SORT_GRAPH_OBJ_MODE { //--- Sort by integer properties SORT_BY_GRAPH_OBJ_ID = 0, // Sort by object ID SORT_BY_GRAPH_OBJ_TYPE, // Sort by object type SORT_BY_GRAPH_OBJ_ELEMENT_TYPE, // Sort by graphical element type SORT_BY_GRAPH_OBJ_BELONG, // Sort by a graphical element affiliation SORT_BY_GRAPH_OBJ_CHART_ID, // Sort by chart ID SORT_BY_GRAPH_OBJ_WND_NUM, // Sort by chart subwindow index SORT_BY_GRAPH_OBJ_NUM, // Sort by object index in the list SORT_BY_GRAPH_OBJ_CREATETIME, // Sort by object creation time SORT_BY_GRAPH_OBJ_TIMEFRAMES, // Sort by object visibility on timeframes SORT_BY_GRAPH_OBJ_BACK, // Sort by the "Background object" property SORT_BY_GRAPH_OBJ_ZORDER, // Sort by the priority of a graphical object for receiving the event of clicking on a chart SORT_BY_GRAPH_OBJ_HIDDEN, // Sort by a disabling display of the name of a graphical object in the terminal object list SORT_BY_GRAPH_OBJ_SELECTED, // Sort by the "Object selection" property SORT_BY_GRAPH_OBJ_SELECTABLE, // Sort by the "Object availability" property SORT_BY_GRAPH_OBJ_TIME, // Sort by time coordinate SORT_BY_GRAPH_OBJ_COLOR, // Sort by color SORT_BY_GRAPH_OBJ_STYLE, // Sort by style SORT_BY_GRAPH_OBJ_WIDTH, // Sort by line width SORT_BY_GRAPH_OBJ_FILL, // Sort by the "Object color filling" property SORT_BY_GRAPH_OBJ_READONLY, // Sort by the ability to edit text in the Edit object SORT_BY_GRAPH_OBJ_LEVELS, // Sort by number of levels SORT_BY_GRAPH_OBJ_LEVELCOLOR, // Sort by line level color SORT_BY_GRAPH_OBJ_LEVELSTYLE, // Sort by line level style SORT_BY_GRAPH_OBJ_LEVELWIDTH, // Sort by line level width SORT_BY_GRAPH_OBJ_ALIGN, // Sort by the "Horizontal text alignment in the Entry field" property SORT_BY_GRAPH_OBJ_FONTSIZE, // Sort by font size SORT_BY_GRAPH_OBJ_RAY_LEFT, // Sort by "Ray goes to the left" property SORT_BY_GRAPH_OBJ_RAY_RIGHT, // Sort by "Ray goes to the right" property SORT_BY_GRAPH_OBJ_RAY, // Sort by the "Vertical line goes through all windows of a chart" property SORT_BY_GRAPH_OBJ_ELLIPSE, // Sort by the "Display the full ellipse of the Fibonacci Arc object" property SORT_BY_GRAPH_OBJ_ARROWCODE, // Sort by an arrow code for the Arrow object SORT_BY_GRAPH_OBJ_ANCHOR, // Sort by the position of a binding point of a graphical object SORT_BY_GRAPH_OBJ_XDISTANCE, // Sort by a distance from the base corner along the X axis in pixels SORT_BY_GRAPH_OBJ_YDISTANCE, // Sort by a distance from the base corner along the Y axis in pixels SORT_BY_GRAPH_OBJ_DIRECTION, // Sort by the "Gann object trend" property SORT_BY_GRAPH_OBJ_DEGREE, // Sort by the "Elliott wave marking level" property SORT_BY_GRAPH_OBJ_DRAWLINES, // Sort by the "Display lines for Elliott wave marking" property SORT_BY_GRAPH_OBJ_STATE, // Sort by button state (pressed/released) SORT_BY_GRAPH_OBJ_OBJ_CHART_ID, // Sort by Chart object ID. SORT_BY_GRAPH_OBJ_CHART_OBJ_PERIOD, // Sort by Chart object period SORT_BY_GRAPH_OBJ_CHART_OBJ_DATE_SCALE, // Sort by time scale display flag for the Chart object SORT_BY_GRAPH_OBJ_CHART_OBJ_PRICE_SCALE, // Sort by price scale display flag for the Chart object SORT_BY_GRAPH_OBJ_CHART_OBJ_CHART_SCALE, // Sort by Chart object scale SORT_BY_GRAPH_OBJ_XSIZE, // Sort by Object width along the X axis in pixels SORT_BY_GRAPH_OBJ_YSIZE, // Sort by object height along the Y axis in pixels SORT_BY_GRAPH_OBJ_XOFFSET, // Sort by X coordinate of the upper-left corner of the visibility area SORT_BY_GRAPH_OBJ_YOFFSET, // Sort by Y coordinate of the upper-left corner of the visibility area SORT_BY_GRAPH_OBJ_BGCOLOR, // Sort by background color for OBJ_EDIT, OBJ_BUTTON and OBJ_RECTANGLE_LABEL SORT_BY_GRAPH_OBJ_CORNER, // Sort by chart corner for binding a graphical object SORT_BY_GRAPH_OBJ_BORDER_TYPE, // Sort by border type for the "Rectangle border" object SORT_BY_GRAPH_OBJ_BORDER_COLOR, // Sort by frame color for the OBJ_EDIT and OBJ_BUTTON objects //--- Sort by real properties SORT_BY_GRAPH_OBJ_PRICE = FIRST_GRAPH_OBJ_DBL_PROP, // Sort by price coordinate SORT_BY_GRAPH_OBJ_LEVELVALUE, // Sort by level value SORT_BY_GRAPH_OBJ_SCALE, // Sort by scale (property of Gann objects and Fibonacci Arcs objects) SORT_BY_GRAPH_OBJ_ANGLE, // Sort by angle SORT_BY_GRAPH_OBJ_DEVIATION, // Sort by a deviation of the standard deviation channel //--- Sort by string properties SORT_BY_GRAPH_OBJ_NAME = FIRST_GRAPH_OBJ_STR_PROP, // Sort by object name SORT_BY_GRAPH_OBJ_TEXT, // Sort by object description SORT_BY_GRAPH_OBJ_TOOLTIP, // Sort by tooltip text SORT_BY_GRAPH_OBJ_LEVELTEXT, // Sort by level description SORT_BY_GRAPH_OBJ_FONT, // Sort by font SORT_BY_GRAPH_OBJ_BMPFILE, // Sort by BMP file name for the "Bitmap Level" object SORT_BY_GRAPH_OBJ_CHART_OBJ_SYMBOL, // Sort by Chart object period symbol }; //+------------------------------------------------------------------+
Nun fügen wir die Texte der neuen Bibliotheksmeldungen und die Beschreibungen aller grafischen Objekteigenschaften hinzu.
Dazu fügen wir die Indizes der neuen Bibliotheksmeldungen in \MQL5\Include\DoEasy\Data.mqh ein:
MSG_LIB_TEXT_JANUARY, // January MSG_LIB_TEXT_FEBRUARY, // February MSG_LIB_TEXT_MARCH, // March MSG_LIB_TEXT_APRIL, // April MSG_LIB_TEXT_MAY, // May MSG_LIB_TEXT_JUNE, // June MSG_LIB_TEXT_JULY, // July MSG_LIB_TEXT_AUGUST, // August MSG_LIB_TEXT_SEPTEMBER, // September MSG_LIB_TEXT_OCTOBER, // October MSG_LIB_TEXT_NOVEMBER, // November MSG_LIB_TEXT_DECEMBER, // December MSG_LIB_TEXT_ALIGN_LEFT, // Left alignment MSG_LIB_TEXT_ALIGN_CENTER, // Center alignment MSG_LIB_TEXT_ALIGN_RIGHT, // Right alignment MSG_LIB_TEXT_GANN_UP_TREND, // Line corresponds to an uptrend MSG_LIB_TEXT_GANN_DOWN_TREND, // Line corresponds to a downtrend MSG_LIB_TEXT_ELLIOTT_GRAND_SUPERCYCLE, // Grand Supercycle MSG_LIB_TEXT_ELLIOTT_SUPERCYCLE, // Supercycle MSG_LIB_TEXT_ELLIOTT_CYCLE, // Cycle MSG_LIB_TEXT_ELLIOTT_PRIMARY, // Primary cycle MSG_LIB_TEXT_ELLIOTT_INTERMEDIATE, // Intermediate MSG_LIB_TEXT_ELLIOTT_MINOR, // Minor cycle MSG_LIB_TEXT_ELLIOTT_MINUTE, // Minute MSG_LIB_TEXT_ELLIOTT_MINUETTE, // Second (Minuette) MSG_LIB_TEXT_ELLIOTT_SUBMINUETTE, // Subsecond (Subminuette) MSG_LIB_TEXT_BUTTON_STATE_PRESSED, // Pressed MSG_LIB_TEXT_BUTTON_STATE_DEPRESSED, // Released MSG_LIB_TEXT_CORNER_LEFT_UPPER, // Center of coordinates at the upper left corner of the chart MSG_LIB_TEXT_CORNER_LEFT_LOWER, // Center of coordinates at the lower left corner of the chart MSG_LIB_TEXT_CORNER_RIGHT_LOWER, // Center of coordinates at the lower right corner of the chart MSG_LIB_TEXT_CORNER_RIGHT_UPPER, // Center of coordinates at the upper right corner of the chart MSG_LIB_TEXT_BORDER_FLAT, // Flat MSG_LIB_TEXT_BORDER_RAISED, // Raised MSG_LIB_TEXT_BORDER_SUNKEN, // Sunken MSG_LIB_TEXT_SUNDAY, // Sunday MSG_LIB_TEXT_MONDAY, // Monday MSG_LIB_TEXT_TUESDAY, // Tuesday MSG_LIB_TEXT_WEDNESDAY, // Wednesday MSG_LIB_TEXT_THURSDAY, // Thursday MSG_LIB_TEXT_FRIDAY, // Friday MSG_LIB_TEXT_SATURDAY, // Saturday
...
//--- CGraphElementsCollection MSG_GRAPH_ELM_COLLECTION_ERR_OBJ_ALREADY_EXISTS, // Error. A chart control object already exists with chart id MSG_GRAPH_ELM_COLLECTION_ERR_FAILED_CREATE_CTRL_OBJ,// Failed to create chart control object with chart ID //--- GStdGraphObj MSG_GRAPH_STD_OBJ_ERR_NOT_FIND_SUBWINDOW, // Failed to find the chart subwindow MSG_GRAPH_ELEMENT_TYPE_STANDART, // Standard graphical object MSG_GRAPH_ELEMENT_TYPE_ELEMENT, // Element MSG_GRAPH_ELEMENT_TYPE_SHADOW_OBJ, // Shadow object MSG_GRAPH_ELEMENT_TYPE_FORM, // Form MSG_GRAPH_ELEMENT_TYPE_WINDOW, // Window MSG_GRAPH_OBJ_BELONG_PROGRAM, // Graphical object belongs to a program MSG_GRAPH_OBJ_BELONG_NO_PROGRAM, // Graphical object does not belong to a program //--- MSG_GRAPH_STD_OBJ_VLINE, // Vertical line MSG_GRAPH_STD_OBJ_HLINE, // Horizontal line MSG_GRAPH_STD_OBJ_TREND, // Trend line MSG_GRAPH_STD_OBJ_TRENDBYANGLE, // Trend line by angle MSG_GRAPH_STD_OBJ_CYCLES, // Cyclic lines MSG_GRAPH_STD_OBJ_ARROWED_LINE, // Arrowed line object MSG_GRAPH_STD_OBJ_CHANNEL, // Equidistant channel MSG_GRAPH_STD_OBJ_STDDEVCHANNEL, // Standard deviation channel MSG_GRAPH_STD_OBJ_REGRESSION, // Linear regression channel MSG_GRAPH_STD_OBJ_PITCHFORK, // Andrews' pitchfork MSG_GRAPH_STD_OBJ_GANNLINE, // Gann line MSG_GRAPH_STD_OBJ_GANNFAN, // Gann fan MSG_GRAPH_STD_OBJ_GANNGRID, // Gann grid MSG_GRAPH_STD_OBJ_FIBO, // Fibo levels MSG_GRAPH_STD_OBJ_FIBOTIMES, // Fibo time zones MSG_GRAPH_STD_OBJ_FIBOFAN, // Fibo fan MSG_GRAPH_STD_OBJ_FIBOARC, // Fibo arcs MSG_GRAPH_STD_OBJ_FIBOCHANNEL, // Fibo channel MSG_GRAPH_STD_OBJ_EXPANSION, // Fibo expansion MSG_GRAPH_STD_OBJ_ELLIOTWAVE5, // Elliott 5 waves MSG_GRAPH_STD_OBJ_ELLIOTWAVE3, // Elliott 3 waves MSG_GRAPH_STD_OBJ_RECTANGLE, // Rectangle MSG_GRAPH_STD_OBJ_TRIANGLE, // Triangle MSG_GRAPH_STD_OBJ_ELLIPSE, // Ellipse MSG_GRAPH_STD_OBJ_ARROW_THUMB_UP, // Thumb up MSG_GRAPH_STD_OBJ_ARROW_THUMB_DOWN, // Thumb down MSG_GRAPH_STD_OBJ_ARROW_UP, // Arrow up MSG_GRAPH_STD_OBJ_ARROW_DOWN, // Arrow down MSG_GRAPH_STD_OBJ_ARROW_STOP, // Stop MSG_GRAPH_STD_OBJ_ARROW_CHECK, // Check mark MSG_GRAPH_STD_OBJ_ARROW_LEFT_PRICE, // Left price label MSG_GRAPH_STD_OBJ_ARROW_RIGHT_PRICE, // Right price label MSG_GRAPH_STD_OBJ_ARROW_BUY, // Buy MSG_GRAPH_STD_OBJ_ARROW_SELL, // Sell MSG_GRAPH_STD_OBJ_ARROW, // Arrow MSG_GRAPH_STD_OBJ_TEXT, // Text MSG_GRAPH_STD_OBJ_LABEL, // Text label MSG_GRAPH_STD_OBJ_BUTTON, // Button MSG_GRAPH_STD_OBJ_CHART, // Chart MSG_GRAPH_STD_OBJ_BITMAP, // Bitmap MSG_GRAPH_STD_OBJ_BITMAP_LABEL, // Bitmap label MSG_GRAPH_STD_OBJ_EDIT, // Edit MSG_GRAPH_STD_OBJ_EVENT, // Event object which corresponds to an event in Economic Calendar MSG_GRAPH_STD_OBJ_RECTANGLE_LABEL, // Rectangle Label object used to create and design the custom graphical interface MSG_GRAPH_OBJ_PROP_ID, // Object ID MSG_GRAPH_OBJ_PROP_TYPE, // Graphical object type (ENUM_OBJECT) MSG_GRAPH_OBJ_PROP_ELEMENT_TYPE, // Graphical element type (ENUM_GRAPH_ELEMENT_TYPE) MSG_GRAPH_OBJ_PROP_BELONG, // Graphical object affiliation MSG_GRAPH_OBJ_PROP_CHART_ID, // Chart ID MSG_GRAPH_OBJ_PROP_WND_NUM, // Chart subwindow index MSG_GRAPH_OBJ_PROP_CREATETIME, // Creation time MSG_GRAPH_OBJ_PROP_TIMEFRAMES, // Object visibility on timeframes MSG_GRAPH_OBJ_PROP_BACK, // Background object MSG_GRAPH_OBJ_PROP_ZORDER, // Priority of a graphical object for receiving the event of clicking on a chart MSG_GRAPH_OBJ_PROP_HIDDEN, // Disable displaying the name of a graphical object in the terminal object list MSG_GRAPH_OBJ_PROP_SELECTED, // Object selection MSG_GRAPH_OBJ_PROP_SELECTABLE, // Object availability MSG_GRAPH_OBJ_PROP_NUM, // Object index in the list MSG_GRAPH_OBJ_PROP_TIME, // Time coordinate MSG_GRAPH_OBJ_PROP_COLOR, // Color MSG_GRAPH_OBJ_PROP_STYLE, // Style MSG_GRAPH_OBJ_PROP_WIDTH, // Line width MSG_GRAPH_OBJ_PROP_FILL, // Object color filling MSG_GRAPH_OBJ_PROP_READONLY, // Ability to edit text in the Edit object MSG_GRAPH_OBJ_PROP_LEVELS, // Number of levels MSG_GRAPH_OBJ_PROP_LEVELCOLOR, // Level line color MSG_GRAPH_OBJ_PROP_LEVELSTYLE, // Level line style MSG_GRAPH_OBJ_PROP_LEVELWIDTH, // Level line width MSG_GRAPH_OBJ_PROP_ALIGN, // Horizontal text alignment in the Edit object (OBJ_EDIT) MSG_GRAPH_OBJ_PROP_FONTSIZE, // Font size MSG_GRAPH_OBJ_PROP_RAY_LEFT, // Ray goes to the left MSG_GRAPH_OBJ_PROP_RAY_RIGHT, // Ray goes to the right MSG_GRAPH_OBJ_PROP_RAY, // Vertical line goes through all windows of a chart MSG_GRAPH_OBJ_PROP_ELLIPSE, // Display the full ellipse of the Fibonacci Arc object MSG_GRAPH_OBJ_PROP_ARROWCODE, // Arrow code for the "Arrow" object MSG_GRAPH_OBJ_PROP_ANCHOR, // Position of the binding point of the graphical object MSG_GRAPH_OBJ_PROP_XDISTANCE, // Distance from the base corner along the X axis in pixels MSG_GRAPH_OBJ_PROP_YDISTANCE, // Distance from the base corner along the Y axis in pixels MSG_GRAPH_OBJ_PROP_DIRECTION, // Gann object trend MSG_GRAPH_OBJ_PROP_DEGREE, // Elliott wave marking level MSG_GRAPH_OBJ_PROP_DRAWLINES, // Display lines for Elliott wave marking MSG_GRAPH_OBJ_PROP_STATE, // Button state (pressed/released) MSG_GRAPH_OBJ_PROP_CHART_OBJ_PERIOD, // Chart object period MSG_GRAPH_OBJ_PROP_CHART_OBJ_DATE_SCALE, // Time scale display flag for the Chart object MSG_GRAPH_OBJ_PROP_CHART_OBJ_PRICE_SCALE, // Price scale display flag for the Chart object MSG_GRAPH_OBJ_PROP_CHART_OBJ_CHART_SCALE, // Chart object scale MSG_GRAPH_OBJ_PROP_XSIZE, // Object width along the X axis in pixels. MSG_GRAPH_OBJ_PROP_YSIZE, // Object height along the Y axis in pixels. MSG_GRAPH_OBJ_PROP_XOFFSET, // X coordinate of the upper-left corner of the visibility area. MSG_GRAPH_OBJ_PROP_YOFFSET, // Y coordinate of the upper-left corner of the visibility area. MSG_GRAPH_OBJ_PROP_BGCOLOR, // Background color for OBJ_EDIT, OBJ_BUTTON, OBJ_RECTANGLE_LABEL MSG_GRAPH_OBJ_PROP_CORNER, // Chart corner for binding a graphical object MSG_GRAPH_OBJ_PROP_BORDER_TYPE, // Border type for "Rectangle border" MSG_GRAPH_OBJ_PROP_BORDER_COLOR, // Border color for OBJ_EDIT and OBJ_BUTTON //--- MSG_GRAPH_OBJ_PROP_PRICE, // Price coordinate MSG_GRAPH_OBJ_PROP_LEVELVALUE, // Level value MSG_GRAPH_OBJ_PROP_SCALE, // Scale (property of Gann objects and Fibonacci Arcs objects) MSG_GRAPH_OBJ_PROP_ANGLE, // Angle MSG_GRAPH_OBJ_PROP_DEVIATION, // Deviation of the standard deviation channel //--- MSG_GRAPH_OBJ_PROP_NAME, // Object name MSG_GRAPH_OBJ_PROP_TEXT, // Object description (text contained in the object) MSG_GRAPH_OBJ_PROP_TOOLTIP, // Tooltip text MSG_GRAPH_OBJ_PROP_LEVELTEXT, // Level description MSG_GRAPH_OBJ_PROP_FONT, // Font MSG_GRAPH_OBJ_PROP_BMPFILE, // BMP file name for the "Bitmap Level" object MSG_GRAPH_OBJ_PROP_SYMBOL, // Symbol for the Chart object }; //+------------------------------------------------------------------+
und die Textmeldungen zu den neu hinzugefügten Indizes:
{"Январь","January"}, {"Февраль","February"}, {"Март","March"}, {"Апрель","April"}, {"Май","May"}, {"Июнь","June"}, {"Июль","July"}, {"Август","August"}, {"Сентябрь","September"}, {"Октябрь","October"}, {"Ноябрь","November"}, {"Декабрь","December"}, {"Выравнивание по левой границе","Left alignment"}, {"Выравнивание по центру","Centered"}, {"Выравнивание по правой границе","Right alignment",}, {"Линия соответствует восходящему тренду","Line corresponding to the uptrend line"}, {"Линия соответствует нисходящему тренду","Line corresponding to the downward trend"}, {"Главный Суперцикл (Grand Supercycle)","Grand Supercycle"}, {"Суперцикл (Supercycle)","Supercycle"}, {"Цикл (Cycle)","Cycle"}, {"Первичный цикл (Primary)","Primary"}, {"Промежуточное звено (Intermediate)","Intermediate"}, {"Второстепенный цикл (Minor)","Minor"}, {"Минута (Minute)","Minute"}, {"Секунда (Minuette)","Minuette"}, {"Субсекунда (Subminuette)","Subminuette"}, {"Нажата","Pressed"}, {"Отжата","Depressed"}, {"Центр координат в левом верхнем углу графика","Center of coordinates is in the upper left corner of the chart"}, {"Центр координат в левом нижнем углу графика","Center of coordinates is in the lower left corner of the chart"}, {"Центр координат в правом нижнем углу графика","Center of coordinates is in the lower right corner of the chart"}, {"Центр координат в правом верхнем углу графика","Center of coordinates is in the upper right corner of the chart"}, {"Плоский вид","Flat form"}, {"Выпуклый вид","Prominent form"}, {"Вогнутый вид","Concave form"}, {"Воскресение","Sunday"}, {"Понедельник","Monday"}, {"Вторник","Tuesday"}, {"Среда","Wednesday"}, {"Четверг","Thursday"}, {"Пятница","Friday"}, {"Суббота","Saturday"},
...
//--- CGraphElementsCollection {"Ошибка. Уже существует объект управления чартами с идентификатором чарта ","Error. A chart control object already exists with chart id "}, {"Не удалось создать объект управления чартами с идентификатором чарта ","Failed to create chart control object with chart id "}, //--- GStdGraphObj {"Не удалось найти подокно графика","Could not find chart subwindow"}, {"Стандартный графический объект","Standard graphic object"}, {"Элемент","Element"}, {"Объект тени","Shadow object"}, {"Форма","Form"}, {"Окно","Window"}, {"Графический объект принадлежит программе","The graphic object belongs to the program"}, {"Графический объект не принадлежит программе","The graphic object does not belong to the program"}, {"Вертикальная линия","Vertical Line"}, {"Горизонтальная линия","Horizontal Line"}, {"Трендовая линия","Trend Line"}, {"Трендовая линия по углу","Trend Line By Angle"}, {"Циклические линии","Cycle Lines"}, {"Линия со стрелкой","Arrowed Line"}, {"Равноудаленный канал","Equidistant Channel"}, {"Канал стандартного отклонения","Standard Deviation Channel"}, {"Канал на линейной регрессии","Linear Regression Channel"}, {"Вилы Эндрюса","Andrews’ Pitchfork"}, {"Линия Ганна","Gann Line"}, {"Веер Ганна","Gann Fan"}, {"Сетка Ганна","Gann Grid"}, {"Уровни Фибоначчи","Fibonacci Retracement"}, {"Временные зоны Фибоначчи","Fibonacci Time Zones"}, {"Веер Фибоначчи","Fibonacci Fan"}, {"Дуги Фибоначчи","Fibonacci Arcs"}, {"Канал Фибоначчи","Fibonacci Channel"}, {"Расширение Фибоначчи","Fibonacci Expansion"}, {"5-волновка Эллиотта","Elliott Motive Wave"}, {"3-волновка Эллиотта","Elliott Correction Wave"}, {"Прямоугольник","Rectangle"}, {"Треугольник","Triangle"}, {"Эллипс","Ellipse"}, {"Знак \"Хорошо\"","Thumbs Up"}, {"Знак \"Плохо\"","Thumbs Down"}, {"Знак \"Стрелка вверх\"","Arrow Up"}, {"Знак \"Стрелка вниз\"","Arrow Down"}, {"Знак \"Стоп\"","Stop Sign"}, {"Знак \"Птичка\"","Check Sign"}, {"Левая ценовая метка","Left Price Label"}, {"Правая ценовая метка","Right Price Label"}, {"Знак \"Buy\"","Buy Sign"}, {"Знак \"Sell\"","Sell Sign"}, {"Стрелка","Arrow"}, {"Текст","Text"}, {"Текстовая метка","Label"}, {"Кнопка","Button"}, {"График","Chart"}, {"Рисунок","Bitmap"}, {"Графическая метка","Bitmap Label"}, {"Поле ввода","Edit"}, {"Событие в экономическом календаре","The \"Event\" object corresponding to an event in the economic calendar"}, {"Прямоугольная метка","The \"Rectangle label\" object for creating and designing the custom graphical interface"}, {"Идентификатор объекта","Object ID"}, {"Тип объекта","Object type"}, {"Тип графического элемента","Graphic element type"}, {"Принадлежность объекта","Object belongs to"}, {"Идентификатор графика объекта","Object chart ID"}, {"Номер подокна графика","Chart subwindow number"}, {"Время создания","Time of creation"}, {"Видимость объекта на таймфреймах","Visibility of an object at timeframes"}, {"Объект на заднем плане","Object in the background"}, {"Приоритет графического объекта на получение события нажатия мышки на графике","Priority of a graphical object for receiving events of clicking on a chart"}, {"Запрет на показ имени графического объекта в списке объектов терминала","Prohibit showing of the name of a graphical object in the terminal objects list"}, {"Выделенность объекта","Object is selected"}, {"Доступность объекта","Object availability"}, {"Номер объекта в списке","Object number in the list"}, {"Координата времени","Time coordinate"}, {"Цвет","Color"}, {"Стиль","Style"}, {"Толщина линии","Line thickness"}, {"Заливка объекта цветом","Fill an object with color"}, {"Возможность редактирования текста","Ability to edit text"}, {"Количество уровней","Number of levels"}, {"Цвет линии-уровня","Color of the line-level"}, {"Стиль линии-уровня","Style of the line-level"}, {"Толщина линии-уровня","Thickness of the line-level"}, {"Горизонтальное выравнивание текста","Horizontal text alignment"}, {"Размер шрифта","Font size"}, {"Луч продолжается влево","Ray goes to the left"}, {"Луч продолжается вправо","Ray goes to the right"}, {"Вертикальная линия продолжается на все окна графика","A vertical line goes through all the windows of a chart"}, {"Отображение полного эллипса","Showing the full ellipse"}, {"Код стрелки","Arrow code"}, {"Положение точки привязки","Location of the anchor point"}, {"Дистанция в пикселях по оси X от угла привязки","The distance in pixels along the X axis from the binding corner"}, {"Дистанция в пикселях по оси Y от угла привязки","The distance in pixels along the Y axis from the binding corner"}, {"Тренд","Trend"}, {"Уровень","Level"}, {"Отображение линий","Displaying lines"}, {"Состояние кнопки","Button state"}, {"Период графика","Chart timeframe"}, {"Отображение шкалы времени","Displaying the time scale"}, {"Отображение ценовой шкалы","Displaying the price scale"}, {"Масштаб графика","Chart scale"}, {"Ширина по оси X в пикселях","Width along the X axis in pixels"}, {"Высота по оси Y в пикселях","Height along the Y axis in pixels"}, {"X-координата левого верхнего угла прямоугольной области видимости","The X coordinate of the upper left corner of the rectangular visible area"}, {"Y-координата левого верхнего угла прямоугольной области видимости","The Y coordinate of the upper left corner of the rectangular visible area"}, {"Цвет фона","Background color"}, {"Угол графика для привязки","The corner of the chart to link a graphical object"}, {"Тип рамки","Border type"}, {"Цвет рамки","Border color"}, {"Координата цены","Price coordinate"}, {"Значение уровня","Level value"}, {"Масштаб","Scale"}, {"Угол","Angle"}, {"Отклонение канала стандартного отклонения","Deviation for the Standard Deviation Channel"}, {"Имя","Name"}, {"Описание","Description"}, {"Текст всплывающей подсказки","The text of a tooltip"}, {"Описание уровня","Level description"}, {"Шрифт","Font"}, {"Имя BMP-файла","BMP-file name"}, {"Символ графика","Chart Symbol"}, }; //+---------------------------------------------------------------------+
Einige grafische Objekteigenschaften haben einen Enumerationstyp. Um die Beschreibungen der Enumerationen zurückzugeben, müssen wir die Funktionen in der Datei der Bibliotheksdienstfunktionen \MQL5\Include\DoEasy\Services\DELib.mqh erstellen:
Die Funktion, die die Beschreibung des Zeilenstils zurückgibt:
//+------------------------------------------------------------------+ //| Return description of the line style | //+------------------------------------------------------------------+ string LineStyleDescription(const ENUM_LINE_STYLE style) { return ( style==STYLE_SOLID ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_SOLID) : style==STYLE_DASH ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_DASH) : style==STYLE_DOT ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_DOT) : style==STYLE_DASHDOT ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_DASHDOT) : style==STYLE_DASHDOTDOT ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_DASHDOTDOT) : "Unknown" ); } //+------------------------------------------------------------------+
Die Funktion gibt die Beschreibung der Ausrichtungsart zurück:
//+------------------------------------------------------------------+ //| Return the alignment type description | //+------------------------------------------------------------------+ string AlignModeDescription(ENUM_ALIGN_MODE align) { return ( align==ALIGN_LEFT ? CMessage::Text(MSG_LIB_TEXT_ALIGN_LEFT) : align==ALIGN_CENTER ? CMessage::Text(MSG_LIB_TEXT_ALIGN_CENTER) : align==ALIGN_RIGHT ? CMessage::Text(MSG_LIB_TEXT_ALIGN_RIGHT) : "Unknown" ); } //+------------------------------------------------------------------+
Die Funktion gibt die Beschreibung der Trendrichtung des Gann-Gitters zurück:
//+------------------------------------------------------------------+ //| Return the description of the Gann grid trend direction | //+------------------------------------------------------------------+ string GannDirectDescription(const ENUM_GANN_DIRECTION direction) { return ( direction==GANN_UP_TREND ? CMessage::Text(MSG_LIB_TEXT_GANN_UP_TREND) : direction==GANN_DOWN_TREND ? CMessage::Text(MSG_LIB_TEXT_GANN_DOWN_TREND) : "Unknown" ); } //+------------------------------------------------------------------+
Die Funktion gibt die Beschreibung der Elliott-Wellen-Markierungsebene zurück:
//+------------------------------------------------------------------+ //| Return the description of the Elliott wave marking level | //+------------------------------------------------------------------+ string ElliotWaveDegreeDescription(const ENUM_ELLIOT_WAVE_DEGREE degree) { return ( degree==ELLIOTT_GRAND_SUPERCYCLE ? CMessage::Text(MSG_LIB_TEXT_ELLIOTT_GRAND_SUPERCYCLE) : degree==ELLIOTT_SUPERCYCLE ? CMessage::Text(MSG_LIB_TEXT_ELLIOTT_SUPERCYCLE) : degree==ELLIOTT_CYCLE ? CMessage::Text(MSG_LIB_TEXT_ELLIOTT_CYCLE) : degree==ELLIOTT_PRIMARY ? CMessage::Text(MSG_LIB_TEXT_ELLIOTT_PRIMARY) : degree==ELLIOTT_INTERMEDIATE ? CMessage::Text(MSG_LIB_TEXT_ELLIOTT_INTERMEDIATE) : degree==ELLIOTT_MINOR ? CMessage::Text(MSG_LIB_TEXT_ELLIOTT_MINOR) : degree==ELLIOTT_MINUTE ? CMessage::Text(MSG_LIB_TEXT_ELLIOTT_MINUTE) : degree==ELLIOTT_MINUETTE ? CMessage::Text(MSG_LIB_TEXT_ELLIOTT_MINUETTE) : degree==ELLIOTT_SUBMINUETTE ? CMessage::Text(MSG_LIB_TEXT_ELLIOTT_SUBMINUETTE) : "Unknown" ); } //+------------------------------------------------------------------+
Die Funktion gibt die Beschreibung der Diagrammecke zurück, relativ zu der die Koordinaten in Pixeln angegeben sind:
//+------------------------------------------------------------------+ //| Return the description of the chart corner, relative to | //| which the coordinates in pixels are specified | //+------------------------------------------------------------------+ string BaseCornerDescription(const ENUM_BASE_CORNER corner) { return ( corner==CORNER_LEFT_UPPER ? CMessage::Text(MSG_LIB_TEXT_CORNER_LEFT_UPPER) : corner==CORNER_LEFT_LOWER ? CMessage::Text(MSG_LIB_TEXT_CORNER_LEFT_LOWER) : corner==CORNER_RIGHT_LOWER ? CMessage::Text(MSG_LIB_TEXT_CORNER_RIGHT_LOWER) : corner==CORNER_RIGHT_UPPER ? CMessage::Text(MSG_LIB_TEXT_CORNER_RIGHT_UPPER) : "Unknown" ); } //+------------------------------------------------------------------+
Die Funktion gibt die Beschreibung des grafischen Objektrahmens zurück:
//+------------------------------------------------------------------+ //| Return the description of the graphical object frame look | //+------------------------------------------------------------------+ string BorderTypeDescription(const ENUM_BORDER_TYPE border_type) { return ( border_type==BORDER_FLAT ? CMessage::Text(MSG_LIB_TEXT_BORDER_FLAT) : border_type==BORDER_RAISED ? CMessage::Text(MSG_LIB_TEXT_BORDER_RAISED) : border_type==BORDER_SUNKEN ? CMessage::Text(MSG_LIB_TEXT_BORDER_SUNKEN) : "Unknown" ); } //+------------------------------------------------------------------+
Die Funktion gibt die Beschreibung des grafischen Standardobjekttyps zurück:
//+------------------------------------------------------------------+ //| Return the description of the standard graphical object type | //+------------------------------------------------------------------+ string StdGraphObjectTypeDescription(const ENUM_OBJECT type) { return ( type==OBJ_VLINE ? CMessage::Text(MSG_GRAPH_STD_OBJ_VLINE) : type==OBJ_HLINE ? CMessage::Text(MSG_GRAPH_STD_OBJ_HLINE) : type==OBJ_TREND ? CMessage::Text(MSG_GRAPH_STD_OBJ_TREND) : type==OBJ_TRENDBYANGLE ? CMessage::Text(MSG_GRAPH_STD_OBJ_TRENDBYANGLE) : type==OBJ_CYCLES ? CMessage::Text(MSG_GRAPH_STD_OBJ_CYCLES) : type==OBJ_ARROWED_LINE ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROWED_LINE) : type==OBJ_CHANNEL ? CMessage::Text(MSG_GRAPH_STD_OBJ_CHANNEL) : type==OBJ_STDDEVCHANNEL ? CMessage::Text(MSG_GRAPH_STD_OBJ_STDDEVCHANNEL) : type==OBJ_REGRESSION ? CMessage::Text(MSG_GRAPH_STD_OBJ_REGRESSION) : type==OBJ_PITCHFORK ? CMessage::Text(MSG_GRAPH_STD_OBJ_PITCHFORK) : type==OBJ_GANNLINE ? CMessage::Text(MSG_GRAPH_STD_OBJ_GANNLINE) : type==OBJ_GANNFAN ? CMessage::Text(MSG_GRAPH_STD_OBJ_GANNFAN) : type==OBJ_GANNGRID ? CMessage::Text(MSG_GRAPH_STD_OBJ_GANNGRID) : type==OBJ_FIBO ? CMessage::Text(MSG_GRAPH_STD_OBJ_FIBO) : type==OBJ_FIBOTIMES ? CMessage::Text(MSG_GRAPH_STD_OBJ_FIBOTIMES) : type==OBJ_FIBOFAN ? CMessage::Text(MSG_GRAPH_STD_OBJ_FIBOFAN) : type==OBJ_FIBOARC ? CMessage::Text(MSG_GRAPH_STD_OBJ_FIBOARC) : type==OBJ_FIBOCHANNEL ? CMessage::Text(MSG_GRAPH_STD_OBJ_FIBOCHANNEL) : type==OBJ_EXPANSION ? CMessage::Text(MSG_GRAPH_STD_OBJ_EXPANSION) : type==OBJ_ELLIOTWAVE5 ? CMessage::Text(MSG_GRAPH_STD_OBJ_ELLIOTWAVE5) : type==OBJ_ELLIOTWAVE3 ? CMessage::Text(MSG_GRAPH_STD_OBJ_ELLIOTWAVE3) : type==OBJ_RECTANGLE ? CMessage::Text(MSG_GRAPH_STD_OBJ_RECTANGLE) : type==OBJ_TRIANGLE ? CMessage::Text(MSG_GRAPH_STD_OBJ_TRIANGLE) : type==OBJ_ELLIPSE ? CMessage::Text(MSG_GRAPH_STD_OBJ_ELLIPSE) : type==OBJ_ARROW_THUMB_UP ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_THUMB_UP) : type==OBJ_ARROW_THUMB_DOWN ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_THUMB_DOWN) : type==OBJ_ARROW_UP ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_UP) : type==OBJ_ARROW_DOWN ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_DOWN) : type==OBJ_ARROW_STOP ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_STOP) : type==OBJ_ARROW_CHECK ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_CHECK) : type==OBJ_ARROW_LEFT_PRICE ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_LEFT_PRICE) : type==OBJ_ARROW_RIGHT_PRICE ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_RIGHT_PRICE) : type==OBJ_ARROW_BUY ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_BUY) : type==OBJ_ARROW_SELL ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW_SELL) : type==OBJ_ARROW ? CMessage::Text(MSG_GRAPH_STD_OBJ_ARROW) : type==OBJ_TEXT ? CMessage::Text(MSG_GRAPH_STD_OBJ_TEXT) : type==OBJ_LABEL ? CMessage::Text(MSG_GRAPH_STD_OBJ_LABEL) : type==OBJ_BUTTON ? CMessage::Text(MSG_GRAPH_STD_OBJ_BUTTON) : type==OBJ_CHART ? CMessage::Text(MSG_GRAPH_STD_OBJ_CHART) : type==OBJ_BITMAP ? CMessage::Text(MSG_GRAPH_STD_OBJ_BITMAP) : type==OBJ_BITMAP_LABEL ? CMessage::Text(MSG_GRAPH_STD_OBJ_BITMAP_LABEL) : type==OBJ_EDIT ? CMessage::Text(MSG_GRAPH_STD_OBJ_EDIT) : type==OBJ_EVENT ? CMessage::Text(MSG_GRAPH_STD_OBJ_EVENT) : type==OBJ_RECTANGLE_LABEL ? CMessage::Text(MSG_GRAPH_STD_OBJ_RECTANGLE_LABEL) : "Unknown" ); } //+------------------------------------------------------------------+
Wie wir sehen können, erhält jede Funktion eine Variable, die einen von der Funktion überprüften Typ angibt. Anschließend wird der an die Funktion übergebene Typ verglichen und seine Beschreibung mit der Methode Text() der Klasse CMessage zurückgegeben.
Wir schreiben in der Datei \MQL5\Include\DoEasy\Objects\Indicators\Buffer.mqh der abstrakten Indikatorpufferklasse die Methode neu, die die Beschreibung des Zeilenstils des Indikatorpuffers zurückgibt. Zuvor hatte die Methode die gleiche Logik wie die neu hinzugefügte Funktion LineStyleDescription() und sah wie folgt aus:
//+------------------------------------------------------------------+ //| Return description of the drawing line style | //+------------------------------------------------------------------+ string CBuffer::GetLineStyleDescription(void) const { return ( this.LineStyle()==STYLE_SOLID ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_SOLID) : this.LineStyle()==STYLE_DASH ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_DASH) : this.LineStyle()==STYLE_DOT ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_DOT) : this.LineStyle()==STYLE_DASHDOT ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_DASHDOT) : this.LineStyle()==STYLE_DASHDOTDOT ? CMessage::Text(MSG_LIB_TEXT_BUFFER_TEXT_STYLE_DASHDOTDOT) : "Unknown" ); } //+------------------------------------------------------------------+
Da wir bereits über die Servicefunktion verfügen, die allen Bibliotheksklassen gemeinsam ist, geben wir einfach das Ergebnis des Aufrufs der Funktion in der Methode zurück:
//+------------------------------------------------------------------+ //| Return description of the drawing line style | //+------------------------------------------------------------------+ string CBuffer::GetLineStyleDescription(void) const { return LineStyleDescription(this.LineStyle()); } //+------------------------------------------------------------------+
Da ich allen grafischen Objekten viele neue Eigenschaften hinzugefügt habe und einige von ihnen allen grafischen Bibliotheksobjekten eigen sind, sollte die Klasse des grafischen Bibliotheksbasisobjekts in \MQL5\Include\DoEasy\Objects\Graph\GBaseObj.mqh überarbeitet werden. Dies ist die Klasse, von der alle Chartobjekte der Bibliothek geerbt werden. Fügen wir die Variablen hinzu, die allen grafischen Objekten gemeinsam sind, und erstellen wir die Methoden zum Setzen und Zurückgeben der Variablenwerte.
Im geschützten Bereich der Klasse deklarieren wir alle benötigten Variablen:
//+------------------------------------------------------------------+ //| GBaseObj.mqh | //| Copyright 2021, MetaQuotes Ltd. | //| https://mql5.com/en/users/artmedia70 | //+------------------------------------------------------------------+ #property copyright "Copyright 2021, MetaQuotes Ltd." #property link "https://mql5.com/en/users/artmedia70" #property version "1.00" #property strict // Necessary for mql4 //+------------------------------------------------------------------+ //| Include files | //+------------------------------------------------------------------+ #include "..\..\Services\DELib.mqh" #include <Graphics\Graphic.mqh> //+------------------------------------------------------------------+ //| Class of the base object of the library graphical objects | //+------------------------------------------------------------------+ class CGBaseObj : public CObject { private: protected: ENUM_OBJECT m_type_graph_obj; // Graphical object type ENUM_GRAPH_ELEMENT_TYPE m_type_element; // Graphical element type ENUM_GRAPH_OBJ_BELONG m_belong; // Program affiliation string m_name_prefix; // Object name prefix string m_name; // Object name long m_chart_id; // Object chart ID long m_object_id; // Object ID long m_zorder; // Priority of a graphical object for receiving the mouse click event int m_subwindow; // Subwindow index int m_shift_y; // Subwindow Y coordinate shift int m_type; // Object type int m_timeframes_visible; // Visibility of an object on timeframes (a set of flags) int m_digits; // Number of decimal places in a quote bool m_visible; // Object visibility bool m_back; // "Background object" flag bool m_selected; // "Object selection" flag bool m_selectable; // "Object availability" flag bool m_hidden; // "Disable displaying the name of a graphical object in the terminal object list" flag datetime m_create_time; // Object creation time //--- Create (1) the object structure and (2) the object from the structure virtual bool ObjectToStruct(void) { return true; } virtual void StructToObject(void){;} public:
Im öffentlichen Teil der Klasse legen Sie die Methoden zur Angabe der Objekteigenschaften fest, die in jedem grafischen Objekt der Bibliothek vorhanden sind:
public: //--- Set the values of the class variables void SetObjectID(const long value) { this.m_object_id=value; } void SetBelong(const ENUM_GRAPH_OBJ_BELONG belong){ this.m_belong=belong; } void SetTypeGraphObject(const ENUM_OBJECT obj) { this.m_type_graph_obj=obj; } void SetTypeElement(const ENUM_GRAPH_ELEMENT_TYPE type) { this.m_type_element=type;} void SetName(const string name) { this.m_name=name; } void SetChartID(const long chart_id) { this.m_chart_id=chart_id; } void SetDigits(const int value) { this.m_digits=value; }
Die Werte der angegebenen Objekteigenschaften, die durch diese Methoden festgelegt werden, werden nur in diesen Variablen gespeichert, weshalb es ausreicht, den an die Methode übergebenen Wert zu der Variablen hinzuzufügen.
Die Eigenschaften, die sowohl in den Klassenvariablen gespeichert als auch im grafischen Objekt selbst angegeben sind, sollten anders gesetzt werden. Zunächst müssen wir die Eigenschaft des grafischen Objekts ändern. Wenn die Anfrage erfolgreich ist, wird derselbe Wert auch in der Klassenvariable gesetzt:
//--- Set the "Background object" flag bool SetBack(const bool flag) { ::ResetLastError(); if(::ObjectSetInteger(this.m_chart_id,this.m_name,OBJPROP_BACK,flag)) { this.m_back=flag; return true; } else CMessage::ToLog(DFUN,::GetLastError(),true); return false; }
Die Funktion zum Setzen eines grafischen Objektwerts verwendet einen asynchronen Aufruf, was bedeutet, dass die Funktion nicht auf die Ausführung des Befehls wartet, der der Warteschlange eines anderen Charts hinzugefügt wurde. Stattdessen gibt sie die Kontrolle sofort zurück.
Wir können also nicht mit Sicherheit sagen, dass eine Funktion, die erfolgreich zur Ereigniswarteschlange hinzugefügt wurde, eindeutig die Eigenschaft eines grafischen Objekts ändert.
Nach der Hilfe, um das Ergebnis der Befehlsausführung zu überprüfen, können wir eine Funktion verwenden, die die angegebene Objekteigenschaft abfragt. Sie sollten jedoch bedenken, dass solche Funktionen am Ende der Warteschlange dieses Charts eingefügt werden und auf das Ausführungsergebnis warten, weshalb sie zeitaufwändig sein können. Diese Funktion sollte bei der Arbeit mit einer großen Anzahl von Objekten in einem Chart berücksichtigt werden.
Für den Moment lasse ich dies unverändert und gehe davon aus, dass der Befehl zum Ändern der Objekteigenschaften erfolgreich funktioniert hat. Wenn ich bei der Verwendung der Bibliothek feststelle, dass grafische Objekteigenschaften nicht gesetzt werden, während die Klassenvariableneigenschaft bereits angegeben ist, werde ich eine Prüfung hinzufügen, um sicherzustellen, dass die grafische Objekteigenschaft tatsächlich geändert wurde.
Betrachten wir nun alle ähnlichen Methoden zum Festlegen von Eigenschaften für das grafische Objekt und die Variablen, die dem öffentlichen Bereich der Klasse hinzugefügt wurden:
//--- Set the "Background object" flag bool SetBack(const bool flag) { ::ResetLastError(); if(::ObjectSetInteger(this.m_chart_id,this.m_name,OBJPROP_BACK,flag)) { this.m_back=flag; return true; } else CMessage::ToLog(DFUN,::GetLastError(),true); return false; } //--- Set the "Object selection" flag bool SetSelected(const bool flag) { ::ResetLastError(); if(::ObjectSetInteger(this.m_chart_id,this.m_name,OBJPROP_SELECTED,flag)) { this.m_selected=flag; return true; } else CMessage::ToLog(DFUN,::GetLastError(),true); return false; } //--- Set the "Object selection" flag bool SetSelectable(const bool flag) { ::ResetLastError(); if(::ObjectSetInteger(this.m_chart_id,this.m_name,OBJPROP_SELECTABLE,flag)) { this.m_selectable=flag; return true; } else CMessage::ToLog(DFUN,::GetLastError(),true); return false; } //--- Set the "Disable displaying the name of a graphical object in the terminal object list" flag bool SetHidden(const bool flag) { ::ResetLastError(); if(::ObjectSetInteger(this.m_chart_id,this.m_name,OBJPROP_SELECTABLE,flag)) { this.m_hidden=flag; return true; } else CMessage::ToLog(DFUN,::GetLastError(),true); return false; } //--- Set the priority of a graphical object for receiving the event of clicking on a chart bool SetZorder(const long value) { ::ResetLastError(); if(::ObjectSetInteger(this.m_chart_id,this.m_name,OBJPROP_ZORDER,value)) { this.m_zorder=value; return true; } else CMessage::ToLog(DFUN,::GetLastError(),true); return false; } //--- Set object visibility on all timeframes bool SetVisible(const bool flag) { long value=(flag ? OBJ_ALL_PERIODS : OBJ_NO_PERIODS); ::ResetLastError(); if(::ObjectSetInteger(this.m_chart_id,this.m_name,OBJPROP_TIMEFRAMES,value)) { this.m_visible=flag; return true; } else CMessage::ToLog(DFUN,::GetLastError(),true); return false; } //--- Set visibility flags on timeframes specified as flags bool SetVisibleOnTimeframe(const int flags) { ::ResetLastError(); if(::ObjectSetInteger(this.m_chart_id,this.m_name,OBJPROP_TIMEFRAMES,flags)) { this.m_timeframes_visible=flags; return true; } else CMessage::ToLog(DFUN,::GetLastError(),true); return false; } //--- Add the visibility flag on a specified timeframe bool SetVisibleOnTimeframe(const ENUM_TIMEFRAMES timeframe) { int flags=this.m_timeframes_visible; switch(timeframe) { case PERIOD_M1 : flags |= OBJ_PERIOD_M1; break; case PERIOD_M2 : flags |= OBJ_PERIOD_M2; break; case PERIOD_M3 : flags |= OBJ_PERIOD_M3; break; case PERIOD_M4 : flags |= OBJ_PERIOD_M4; break; case PERIOD_M5 : flags |= OBJ_PERIOD_M5; break; case PERIOD_M6 : flags |= OBJ_PERIOD_M6; break; case PERIOD_M10 : flags |= OBJ_PERIOD_M10; break; case PERIOD_M12 : flags |= OBJ_PERIOD_M12; break; case PERIOD_M15 : flags |= OBJ_PERIOD_M15; break; case PERIOD_M20 : flags |= OBJ_PERIOD_M20; break; case PERIOD_M30 : flags |= OBJ_PERIOD_M30; break; case PERIOD_H1 : flags |= OBJ_PERIOD_H1; break; case PERIOD_H2 : flags |= OBJ_PERIOD_H2; break; case PERIOD_H3 : flags |= OBJ_PERIOD_H3; break; case PERIOD_H4 : flags |= OBJ_PERIOD_H4; break; case PERIOD_H6 : flags |= OBJ_PERIOD_H6; break; case PERIOD_H8 : flags |= OBJ_PERIOD_H8; break; case PERIOD_H12 : flags |= OBJ_PERIOD_H12; break; case PERIOD_D1 : flags |= OBJ_PERIOD_D1; break; case PERIOD_W1 : flags |= OBJ_PERIOD_W1; break; case PERIOD_MN1 : flags |= OBJ_PERIOD_MN1; break; default : return true; } ::ResetLastError(); if(::ObjectSetInteger(this.m_chart_id,this.m_name,OBJPROP_TIMEFRAMES,flags)) { this.m_timeframes_visible=flags; return true; } else CMessage::ToLog(DFUN,::GetLastError(),true); return false; } //--- Set a subwindow index bool SetSubwindow(const long chart_id,const string name) { ::ResetLastError(); this.m_subwindow=::ObjectFind(chart_id,name); if(this.m_subwindow<0) CMessage::ToLog(DFUN,MSG_GRAPH_STD_OBJ_ERR_NOT_FIND_SUBWINDOW); return(this.m_subwindow>WRONG_VALUE); } bool SetSubwindow(void) { return this.SetSubwindow(this.m_chart_id,this.m_name); } //--- Return the values of class variables
Als Nächstes fügen wir die Methoden hinzu, die Werte von Klassenvariablen zurückgeben:
//--- Return the values of class variables ENUM_GRAPH_ELEMENT_TYPE TypeGraphElement(void) const { return this.m_type_element; } ENUM_GRAPH_OBJ_BELONG Belong(void) const { return this.m_belong; } ENUM_OBJECT TypeGraphObject(void) const { return this.m_type_graph_obj; } datetime TimeCreate(void) const { return this.m_create_time; } string Name(void) const { return this.m_name; } long ChartID(void) const { return this.m_chart_id; } long ObjectID(void) const { return this.m_object_id; } long Zorder(void) const { return this.m_zorder; } int SubWindow(void) const { return this.m_subwindow; } int ShiftY(void) const { return this.m_shift_y; } int VisibleOnTimeframes(void) const { return this.m_timeframes_visible; } int Digits(void) const { return this.m_digits; } bool IsBack(void) const { return this.m_back; } bool IsSelected(void) const { return this.m_selected; } bool IsSelectable(void) const { return this.m_selectable; } bool IsHidden(void) const { return this.m_hidden; } bool IsVisible(void) const { return this.m_visible; } //--- Return the object visibility flag on a specified timeframe bool IsVisibleOnTimeframe(const ENUM_TIMEFRAMES timeframe) const { return((this.m_timeframes_visible & timeframe)==timeframe); } //--- Return the graphical object type (ENUM_OBJECT) calculated from the object type (ENUM_OBJECT_DE_TYPE) passed to the method ENUM_OBJECT GraphObjectType(const ENUM_OBJECT_DE_TYPE obj_type) const { return ENUM_OBJECT(obj_type-OBJECT_DE_TYPE_GSTD_OBJ-1); } //--- Return the description of the graphical object type
Alle Methoden geben die in den entsprechenden Klassenvariablen festgelegten Werte zurück.
Die Methode GraphObjectType() berechnet den graphischen Objekttyp aus dem Wert des Objekttyps, so dass es möglich ist, den ENUM_OBJECT Standard-Enumerationstyp aus dem Objekttyp zu erhalten, der durch den Enumerationstyp der Bibliothek ENUM_OBJECT_DE_TYPE repräsentiert wird.
Als Nächstes deklarieren wir die Methoden zur Rückgabe von Objekttypbeschreibungen und deren Zugehörigkeit:
//--- Return the description of the type of the graphical (1) object, (2) element and (3) graphical object affiliation string TypeGraphObjectDescription(void); string TypeElementDescription(void); string BelongDescription(void); //--- The virtual method returning the object type virtual int Type(void) const { return this.m_type; } //--- Constructor/destructor CGBaseObj(); ~CGBaseObj(){;} }; //+------------------------------------------------------------------+
Setzen Sie im Klassenkonstruktor Standardwerte für alle Klassenvariablen:
//+------------------------------------------------------------------+ //| Constructor | //+------------------------------------------------------------------+ CGBaseObj::CGBaseObj() : m_shift_y(0),m_visible(false), m_name_prefix(::MQLInfoString(MQL_PROGRAM_NAME)+"_"),m_belong(GRAPH_OBJ_BELONG_PROGRAM) { this.m_type=OBJECT_DE_TYPE_GBASE; // Object type this.m_type_graph_obj=WRONG_VALUE; // Graphical object type this.m_type_element=WRONG_VALUE; // Graphical object type this.m_belong=WRONG_VALUE; // Program/terminal affiliation this.m_name_prefix=""; // Object name prefix this.m_name=""; // Object name this.m_chart_id=0; // Object chart ID this.m_object_id=0; // Object ID this.m_zorder=0; // Priority of a graphical object for receiving the mouse click event this.m_subwindow=0; // Subwindow index this.m_shift_y=0; // Subwindow Y coordinate shift this.m_timeframes_visible=OBJ_ALL_PERIODS; // Visibility of an object on timeframes (a set of flags) this.m_visible=true; // Object visibility this.m_back=false; // "Background object" flag this.m_selected=false; // "Object selection" flag this.m_selectable=false; // "Object availability" flag this.m_hidden=true; // "Disable displaying the name of a graphical object in the terminal object list" flag this.m_create_time=0; // Object creation time } //+------------------------------------------------------------------+
Später werden die abgeleiteten Klassen es uns ermöglichen, die genauen Werte dieser Variablen entsprechend den Werten der Eigenschaften eines durch die Nachfolgeklasse beschriebenen grafischen Objekts festzulegen.
Implementierung der Methode, die die Beschreibung des grafischen Objekttyps zurückgibt:
//+------------------------------------------------------------------+ //| Return the description of the graphical object type | //+------------------------------------------------------------------+ string CGBaseObj::TypeGraphObjectDescription(void) { if(this.TypeGraphElement()==GRAPH_ELEMENT_TYPE_STANDART) return StdGraphObjectTypeDescription(this.m_type_graph_obj); else return this.TypeElementDescription(); } //+------------------------------------------------------------------+
Hier definieren wir zunächst den Typ des grafischen Elements, zu dem das grafische Objekt gehört. Wenn es sich um ein grafisches Standardobjekt handelt, geben wir seine Beschreibung mit Hilfe der Servicefunktion StdGraphObjectTypeDescription() zurück, die ich oben dargestellt habe.
Andernfalls geben wir die Beschreibung des grafischen Elementtyps mit Hilfe der unten beschriebenen Methode TypeElementDescription() zurück:
//+------------------------------------------------------------------+ //| Return the description of the graphical element type | //+------------------------------------------------------------------+ string CGBaseObj::TypeElementDescription(void) { return ( this.TypeGraphElement()==GRAPH_ELEMENT_TYPE_STANDART ? CMessage::Text(MSG_GRAPH_ELEMENT_TYPE_STANDART) : this.TypeGraphElement()==GRAPH_ELEMENT_TYPE_ELEMENT ? CMessage::Text(MSG_GRAPH_ELEMENT_TYPE_ELEMENT) : this.TypeGraphElement()==GRAPH_ELEMENT_TYPE_SHADOW_OBJ ? CMessage::Text(MSG_GRAPH_ELEMENT_TYPE_SHADOW_OBJ) : this.TypeGraphElement()==GRAPH_ELEMENT_TYPE_FORM ? CMessage::Text(MSG_GRAPH_ELEMENT_TYPE_FORM) : this.TypeGraphElement()==GRAPH_ELEMENT_TYPE_WINDOW ? CMessage::Text(MSG_GRAPH_ELEMENT_TYPE_WINDOW) : "Unknown" ); } //+------------------------------------------------------------------+
Die Methode gibt die Beschreibung der Zugehörigkeit des grafischen Objekts zurück:
//+------------------------------------------------------------------+ //| Return the description of the graphical object affiliation | //+------------------------------------------------------------------+ string CGBaseObj::BelongDescription(void) { return ( this.Belong()==GRAPH_OBJ_BELONG_PROGRAM ? CMessage::Text(MSG_GRAPH_OBJ_BELONG_PROGRAM) : this.Belong()==GRAPH_OBJ_BELONG_NO_PROGRAM ? CMessage::Text(MSG_GRAPH_OBJ_BELONG_NO_PROGRAM) : "Unknown" ); } //+------------------------------------------------------------------+
Die Logik der letzten beiden Methoden ähnelt der Logik der oben betrachteten Servicefunktionen.
Die Klasse des abstrakten Grafikobjekts
Wir haben nun alle vorbereitenden Schritte durchlaufen. Lassen Sie uns nun die Klasse des abstrakten Grafikobjekts erstellen.
Wir erstellen in \MQL5\Include\DoEasy\Objects\Graph\ den Ordner Standart\ mit der neuen Datei GStdGraphObj.mqh der Klasse CGStdGraphObj.
Die Klasse sollte von der Klasse des grafischen Basisobjekts aller grafischen Objekte der CGBaseObj-Bibliothek abgeleitet sein. Die Datei des grafischen Objekts sollte auch in die neue Datei der erstellten Klasse eingeschlossen werden:
//+------------------------------------------------------------------+ //| GStdGraphObj.mqh | //| Copyright 2021, MetaQuotes Ltd. | //| https://mql5.com/en/users/artmedia70 | //+------------------------------------------------------------------+ #property copyright "Copyright 2021, MetaQuotes Ltd." #property link "https://mql5.com/en/users/artmedia70" #property version "1.00" #property strict // Necessary for mql4 //+------------------------------------------------------------------+ //| Include files | //+------------------------------------------------------------------+ #include "..\GBaseObj.mqh" //+------------------------------------------------------------------+ //| The class of the abstract standard graphical object | //+------------------------------------------------------------------+ class CGStdGraphObj : public CGBaseObj { }
Im privaten Abschnitt der Klasse platzieren wir die Arrays für die Speicherung von Objekteigenschaften und Methoden für die Rückgabe eines realen Eigenschaftsindexes in das entsprechende Array:
//+------------------------------------------------------------------+ //| The class of the abstract standard graphical object | //+------------------------------------------------------------------+ class CGStdGraphObj : public CGBaseObj { private: long m_long_prop[GRAPH_OBJ_PROP_INTEGER_TOTAL]; // Integer properties double m_double_prop[GRAPH_OBJ_PROP_DOUBLE_TOTAL]; // Real properties string m_string_prop[GRAPH_OBJ_PROP_STRING_TOTAL]; // String properties //--- Return the index of the array the (1) double and (2) string properties are actually located at int IndexProp(ENUM_GRAPH_OBJ_PROP_DOUBLE property) const { return(int)property-GRAPH_OBJ_PROP_INTEGER_TOTAL; } int IndexProp(ENUM_GRAPH_OBJ_PROP_STRING property) const { return(int)property-GRAPH_OBJ_PROP_INTEGER_TOTAL-GRAPH_OBJ_PROP_DOUBLE_TOTAL; } public:
Einstellungen der Methoden, die für alle Bibliotheksobjekte im öffentlichen Abschnitt der Klasse standardmäßig vorhanden sind, sowie zwei Konstruktoren — den Standardkonstruktor und den geschlossenen parametrischen Konstruktor:
public: //--- Set object's (1) integer, (2) real and (3) string properties void SetProperty(ENUM_GRAPH_OBJ_PROP_INTEGER property,long value) { this.m_long_prop[property]=value; } void SetProperty(ENUM_GRAPH_OBJ_PROP_DOUBLE property,double value) { this.m_double_prop[this.IndexProp(property)]=value; } void SetProperty(ENUM_GRAPH_OBJ_PROP_STRING property,string value) { this.m_string_prop[this.IndexProp(property)]=value; } //--- Return object’s (1) integer, (2) real and (3) string property from the properties array long GetProperty(ENUM_GRAPH_OBJ_PROP_INTEGER property) const { return this.m_long_prop[property]; } double GetProperty(ENUM_GRAPH_OBJ_PROP_DOUBLE property) const { return this.m_double_prop[this.IndexProp(property)]; } string GetProperty(ENUM_GRAPH_OBJ_PROP_STRING property) const { return this.m_string_prop[this.IndexProp(property)]; } //--- Return itself CGStdGraphObj *GetObject(void) { return &this;} //--- Return the flag of the object supporting this property virtual bool SupportProperty(ENUM_GRAPH_OBJ_PROP_INTEGER property) { return true; } virtual bool SupportProperty(ENUM_GRAPH_OBJ_PROP_DOUBLE property) { return true; } virtual bool SupportProperty(ENUM_GRAPH_OBJ_PROP_STRING property) { return true; } //--- Get description of (1) integer, (2) real and (3) string properties string GetPropertyDescription(ENUM_GRAPH_OBJ_PROP_INTEGER property); string GetPropertyDescription(ENUM_GRAPH_OBJ_PROP_DOUBLE property); string GetPropertyDescription(ENUM_GRAPH_OBJ_PROP_STRING property); //--- Return the description of the graphical object anchor point position virtual string AnchorDescription(void) const { return (string)this.GetProperty(GRAPH_OBJ_PROP_ANCHOR);} //--- Display the description of the object properties in the journal (full_prop=true - all properties, false - supported ones only - implemented in descendant classes) virtual void Print(const bool full_prop=false,const bool dash=false); //--- Display a short description of the object in the journal virtual void PrintShort(const bool dash=false,const bool symbol=false); //--- Return the object short name virtual string Header(const bool symbol=false); //--- Compare CGStdGraphObj objects by a specified property (to sort the list by an object property) virtual int Compare(const CObject *node,const int mode=0) const; //--- Compare CGStdGraphObj objects with each other by all properties (to search for equal objects) bool IsEqual(CGStdGraphObj* compared_req) const; //--- Default constructor CGStdGraphObj(){ this.m_type=OBJECT_DE_TYPE_GSTD_OBJ; } protected: //--- Protected parametric constructor CGStdGraphObj(const ENUM_OBJECT_DE_TYPE obj_type,const ENUM_GRAPH_OBJ_BELONG belong,const long chart_id,const string name); public: //+--------------------------------------------------------------------+ //|Methods of simplified access and setting graphical object properties| //+--------------------------------------------------------------------+
In diesem Fall gibt die Methode, die die Beschreibung der Ankerpunktposition des grafischen Objekts zurückgibt, eine Zahl und nicht die Beschreibung selbst zurück. Verschiedene Objekte zur Angabe von Ankerpunkten verwenden unterschiedliche Enumerationen. Daher wird die Methode virtuell gemacht und in nachgeordneten Objekten mit solchen Eigenschaften neu definiert.
Als Nächstes verwenden Sie den Klassencode, um die Methoden für einen vereinfachten Zugang zum Setzen und Zurückgeben von Objekteigenschaften hinzuzufügen:
public: //+--------------------------------------------------------------------+ //|Methods of simplified access and setting graphical object properties| //+--------------------------------------------------------------------+ //--- Object index in the list int Number(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_NUM); } void SetNumber(const int number) { this.SetProperty(GRAPH_OBJ_PROP_NUM,number); } //--- Object ID long ObjectID(void) const { return this.GetProperty(GRAPH_OBJ_PROP_ID); } void SetObjectID(const long obj_id) { CGBaseObj::SetObjectID(obj_id); this.SetProperty(GRAPH_OBJ_PROP_ID,obj_id); } //--- Graphical object type ENUM_OBJECT GraphObjectType(void) const { return (ENUM_OBJECT)this.GetProperty(GRAPH_OBJ_PROP_TYPE); } void SetGraphObjectType(const ENUM_OBJECT obj_type) { CGBaseObj::SetTypeGraphObject(obj_type); this.SetProperty(GRAPH_OBJ_PROP_TYPE,obj_type); } //--- Graphical element type ENUM_GRAPH_ELEMENT_TYPE GraphElementType(void) const { return (ENUM_GRAPH_ELEMENT_TYPE)this.GetProperty(GRAPH_OBJ_PROP_ELEMENT_TYPE); } void SetGraphElementType(const ENUM_GRAPH_ELEMENT_TYPE elm_type) { CGBaseObj::SetTypeElement(elm_type); this.SetProperty(GRAPH_OBJ_PROP_ELEMENT_TYPE,elm_type); } //--- Graphical object affiliation ENUM_GRAPH_OBJ_BELONG Belong(void) const { return (ENUM_GRAPH_OBJ_BELONG)this.GetProperty(GRAPH_OBJ_PROP_BELONG); } void SetBelong(const ENUM_GRAPH_OBJ_BELONG belong) { CGBaseObj::SetBelong(belong); this.SetProperty(GRAPH_OBJ_PROP_BELONG,belong); } //--- Chart ID long ChartID(void) const { return this.GetProperty(GRAPH_OBJ_PROP_CHART_ID); } void SetChartID(const long chart_id) { CGBaseObj::SetChartID(chart_id); this.SetProperty(GRAPH_OBJ_PROP_CHART_ID,chart_id); } //--- Chart subwindow index int SubWindow(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_WND_NUM); } void SetSubWindow(void) { if(CGBaseObj::SetSubwindow(CGBaseObj::ChartID(),CGBaseObj::Name())) this.SetProperty(GRAPH_OBJ_PROP_WND_NUM,CGBaseObj::SubWindow()); } //--- Object creation time datetime TimeCteate(void) const { return (datetime)this.GetProperty(GRAPH_OBJ_PROP_CREATETIME); } //--- Object visibility on timeframes bool Visible(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_TIMEFRAMES); } void SetFlagVisible(const bool flag) { if(CGBaseObj::SetVisible(flag)) this.SetProperty(GRAPH_OBJ_PROP_TIMEFRAMES,flag); } //--- Background object bool Back(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_BACK); } void SetFlagBack(const bool flag) { if(CGBaseObj::SetBack(flag)) this.SetProperty(GRAPH_OBJ_PROP_BACK,flag); } //--- Priority of a graphical object for receiving the event of clicking on a chart long Zorder(void) const { return this.GetProperty(GRAPH_OBJ_PROP_ZORDER); } void SetZorder(const long value) { if(CGBaseObj::SetZorder(value)) this.SetProperty(GRAPH_OBJ_PROP_ZORDER,value); } //--- Disable displaying the name of a graphical object in the terminal object list bool Hidden(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_HIDDEN); } void SetFlagHidden(const bool flag) { if(CGBaseObj::SetHidden(flag)) this.SetProperty(GRAPH_OBJ_PROP_HIDDEN,flag); } //--- Object selection bool Selected(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_SELECTED); } void SetFlagSelected(const bool flag) { if(CGBaseObj::SetSelected(flag)) this.SetProperty(GRAPH_OBJ_PROP_SELECTED,flag); } //--- Object availability bool Selectable(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_SELECTABLE); } void SetFlagSelectable(const bool flag) { if(CGBaseObj::SetSelectable(flag)) this.SetProperty(GRAPH_OBJ_PROP_SELECTABLE,flag); } //--- Time coordinate datetime Time(void) const { return (datetime)this.GetProperty(GRAPH_OBJ_PROP_TIME); } void SetTime(const datetime time) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_TIME,time)) this.SetProperty(GRAPH_OBJ_PROP_TIME,time); } //--- Color color Color(void) const { return (color)this.GetProperty(GRAPH_OBJ_PROP_COLOR); } void SetColor(const color colour) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_COLOR,colour)) this.SetProperty(GRAPH_OBJ_PROP_COLOR,colour); } //--- Style ENUM_LINE_STYLE Style(void) const { return (ENUM_LINE_STYLE)this.GetProperty(GRAPH_OBJ_PROP_STYLE); } void SetStyle(const ENUM_LINE_STYLE style) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_STYLE,style)) this.SetProperty(GRAPH_OBJ_PROP_STYLE,style); } //--- Line width int Width(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_WIDTH); } void SetWidth(const int width) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_WIDTH,width)) this.SetProperty(GRAPH_OBJ_PROP_WIDTH,width); } //--- Object color filling bool Fill(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_FILL); } void SetFlagFill(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_FILL,flag)) this.SetProperty(GRAPH_OBJ_PROP_FILL,flag); } //--- Ability to edit text in the Edit object bool ReadOnly(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_READONLY); } void SetFlagReadOnly(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_READONLY,flag)) this.SetProperty(GRAPH_OBJ_PROP_READONLY,flag); } //--- Number of levels int Levels(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_LEVELS); } void SetLevels(const int levels) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_LEVELS,levels)) this.SetProperty(GRAPH_OBJ_PROP_LEVELS,levels); } //--- Line level color color LevelColor(void) const { return (color)this.GetProperty(GRAPH_OBJ_PROP_LEVELCOLOR); } void SetLevelColor(const color colour) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_LEVELCOLOR,colour)) this.SetProperty(GRAPH_OBJ_PROP_LEVELCOLOR,colour); } //--- Level line style ENUM_LINE_STYLE LevelStyle(void) const { return (ENUM_LINE_STYLE)this.GetProperty(GRAPH_OBJ_PROP_LEVELSTYLE); } void SetLevelStyle(const ENUM_LINE_STYLE style) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_LEVELSTYLE,style)) this.SetProperty(GRAPH_OBJ_PROP_LEVELSTYLE,style); } ///--- Level line width int LevelWidth(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_LEVELWIDTH); } void SetLevelWidth(const int width) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_LEVELWIDTH,width)) this.SetProperty(GRAPH_OBJ_PROP_LEVELWIDTH,width); } //--- Horizontal text alignment in the Edit object (OBJ_EDIT) ENUM_ALIGN_MODE Align(void) const { return (ENUM_ALIGN_MODE)this.GetProperty(GRAPH_OBJ_PROP_ALIGN); } void SetAlign(const ENUM_ALIGN_MODE align) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_ALIGN,align)) this.SetProperty(GRAPH_OBJ_PROP_ALIGN,align); } //--- Font size int FontSize(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_FONTSIZE); } void SetFontSize(const int size) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_FONTSIZE,size)) this.SetProperty(GRAPH_OBJ_PROP_FONTSIZE,size); } //--- Ray goes to the left bool RayLeft(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_RAY_LEFT); } void SetFlagRayLeft(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_RAY_LEFT,flag)) this.SetProperty(GRAPH_OBJ_PROP_RAY_LEFT,flag); } //--- Ray goes to the right bool RayRight(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_RAY_RIGHT); } void SetFlagRayRight(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_RAY_RIGHT,flag)) this.SetProperty(GRAPH_OBJ_PROP_RAY_RIGHT,flag); } //--- Vertical line goes through all windows of a chart bool Ray(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_RAY); } void SetFlagRay(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_RAY,flag)) this.SetProperty(GRAPH_OBJ_PROP_RAY,flag); } //--- Display the full ellipse of the Fibonacci Arc object bool Ellipse(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_ELLIPSE); } void SetFlagEllipse(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_ELLIPSE,flag)) this.SetProperty(GRAPH_OBJ_PROP_ELLIPSE,flag); } //--- Arrow code for the "Arrow" object uchar ArrowCode(void) const { return (uchar)this.GetProperty(GRAPH_OBJ_PROP_ARROWCODE); } void SetArrowCode(const uchar code) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_ARROWCODE,code)) this.SetProperty(GRAPH_OBJ_PROP_ARROWCODE,code); } //--- Position of the graphical object anchor point int Anchor(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_ANCHOR); } void SetAnchor(const int anchor) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_ANCHOR,anchor)) this.SetProperty(GRAPH_OBJ_PROP_ANCHOR,anchor); } //--- Distance from the base corner along the X axis in pixels int XDistance(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_XDISTANCE); } void SetXDistance(const int distance) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_XDISTANCE,distance)) this.SetProperty(GRAPH_OBJ_PROP_XDISTANCE,distance); } //--- Distance from the base corner along the Y axis in pixels int YDistance(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_YDISTANCE); } void SetYDistance(const int distance) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_YDISTANCE,distance)) this.SetProperty(GRAPH_OBJ_PROP_YDISTANCE,distance); } //--- Gann object trend ENUM_GANN_DIRECTION Direction(void) const { return (ENUM_GANN_DIRECTION)this.GetProperty(GRAPH_OBJ_PROP_DIRECTION); } void SetDirection(const ENUM_GANN_DIRECTION direction) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_DIRECTION,direction)) this.SetProperty(GRAPH_OBJ_PROP_DIRECTION,direction); } //--- Elliott wave marking level ENUM_ELLIOT_WAVE_DEGREE Degree(void) const { return (ENUM_ELLIOT_WAVE_DEGREE)this.GetProperty(GRAPH_OBJ_PROP_DEGREE); } void SetDegree(const ENUM_ELLIOT_WAVE_DEGREE degree) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_DEGREE,degree)) this.SetProperty(GRAPH_OBJ_PROP_DEGREE,degree); } //--- Display lines for Elliott wave marking bool DrawLines(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_DRAWLINES); } void SetFlagDrawLines(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_DRAWLINES,flag)) this.SetProperty(GRAPH_OBJ_PROP_DRAWLINES,flag); } //--- Button state (pressed/released) bool State(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_STATE); } void SetFlagState(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_STATE,flag)) this.SetProperty(GRAPH_OBJ_PROP_STATE,flag); } //--- Chart object ID (OBJ_CHART) long ChartObjChartID(void) const { return this.GetProperty(GRAPH_OBJ_PROP_OBJ_CHART_ID); } void SetChartObjChartID(const long chart_id) { this.SetProperty(GRAPH_OBJ_PROP_OBJ_CHART_ID,chart_id); } //--- Chart object period ENUM_TIMEFRAMES ChartObjPeriod(void) const { return (ENUM_TIMEFRAMES)this.GetProperty(GRAPH_OBJ_PROP_CHART_OBJ_PERIOD); } void SetChartObjPeriod(const ENUM_TIMEFRAMES timeframe) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_PERIOD,timeframe)) this.SetProperty(GRAPH_OBJ_PROP_CHART_OBJ_PERIOD,timeframe); } //--- Time scale display flag for the Chart object bool ChartObjDateScale(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_CHART_OBJ_DATE_SCALE); } void SetFlagChartObjDateScale(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_DATE_SCALE,flag)) this.SetProperty(GRAPH_OBJ_PROP_CHART_OBJ_DATE_SCALE,flag); } //--- Price scale display flag for the Chart object bool ChartObjPriceScale(void) const { return (bool)this.GetProperty(GRAPH_OBJ_PROP_CHART_OBJ_PRICE_SCALE); } void SetFlagPriceScale(const bool flag) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_PRICE_SCALE,flag)) this.SetProperty(GRAPH_OBJ_PROP_CHART_OBJ_PRICE_SCALE,flag); } //--- Chart object scale int ChartObjChartScale(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_CHART_OBJ_CHART_SCALE); } void SetChartObjChartScale(const int scale) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_CHART_SCALE,scale)) this.SetProperty(GRAPH_OBJ_PROP_CHART_OBJ_CHART_SCALE,scale); } //--- Object width along the X axis in pixels int XSize(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_XSIZE); } void SetXSize(const int size) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_XSIZE,size)) this.SetProperty(GRAPH_OBJ_PROP_XSIZE,size); } //--- Object height along the Y axis in pixels int YSize(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_YSIZE); } void SetYSize(const int size) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_YSIZE,size)) this.SetProperty(GRAPH_OBJ_PROP_YSIZE,size); } //--- X coordinate of the upper-left corner of the visibility area int XOffset(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_XOFFSET); } void SetXOffset(const int offset) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_XOFFSET,offset)) this.SetProperty(GRAPH_OBJ_PROP_XOFFSET,offset); } //--- Y coordinate of the upper-left corner of the visibility area int YOffset(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_YOFFSET); } void SetYOffset(const int offset) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_YOFFSET,offset)) this.SetProperty(GRAPH_OBJ_PROP_YOFFSET,offset); } //--- Background color for OBJ_EDIT, OBJ_BUTTON, OBJ_RECTANGLE_LABEL color BGColor(void) const { return (color)this.GetProperty(GRAPH_OBJ_PROP_BGCOLOR); } void SetBGColor(const color colour) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_BGCOLOR,colour)) this.SetProperty(GRAPH_OBJ_PROP_BGCOLOR,colour); } //--- Chart corner for attaching a graphical object ENUM_BASE_CORNER Corner(void) const { return (ENUM_BASE_CORNER)this.GetProperty(GRAPH_OBJ_PROP_CORNER); } void SetCorner(const ENUM_BASE_CORNER corner) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_CORNER,corner)) this.SetProperty(GRAPH_OBJ_PROP_CORNER,corner); } //--- Border type for the Rectangle label object ENUM_BORDER_TYPE BorderType(void) const { return (ENUM_BORDER_TYPE)this.GetProperty(GRAPH_OBJ_PROP_BORDER_TYPE); } void SetBorderType(const ENUM_BORDER_TYPE type) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_BORDER_TYPE,type)) this.SetProperty(GRAPH_OBJ_PROP_BORDER_TYPE,type); } //--- Border color for OBJ_EDIT and OBJ_BUTTON color BorderColor(void) const { return (color)this.GetProperty(GRAPH_OBJ_PROP_BORDER_COLOR); } void SetBorderColor(const color colour) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_BORDER_COLOR,colour)) this.SetProperty(GRAPH_OBJ_PROP_BORDER_COLOR,colour); } //--- Price coordinate double Price(void) const { return this.GetProperty(GRAPH_OBJ_PROP_PRICE); } void SetPrice(const double price) { if(::ObjectSetDouble(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_PRICE,price)) this.SetProperty(GRAPH_OBJ_PROP_PRICE,price); } //--- Level value double LevelValue(void) const { return this.GetProperty(GRAPH_OBJ_PROP_LEVELVALUE); } void SetLevelValue(const double value) { if(::ObjectSetDouble(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_LEVELVALUE,value)) this.SetProperty(GRAPH_OBJ_PROP_LEVELVALUE,value); } //--- Scale double Scale(void) const { return this.GetProperty(GRAPH_OBJ_PROP_SCALE); } void SetScale(const double scale) { if(::ObjectSetDouble(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_SCALE,scale)) this.SetProperty(GRAPH_OBJ_PROP_SCALE,scale); } //--- Angle double Angle(void) const { return this.GetProperty(GRAPH_OBJ_PROP_ANGLE); } void SetAngle(const double angle) { if(::ObjectSetDouble(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_ANGLE,angle)) this.SetProperty(GRAPH_OBJ_PROP_ANGLE,angle); } //--- Deviation of the standard deviation channel double Deviation(void) const { return this.GetProperty(GRAPH_OBJ_PROP_DEVIATION); } void SetDeviation(const double deviation) { if(::ObjectSetDouble(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_DEVIATION,deviation)) this.SetProperty(GRAPH_OBJ_PROP_DEVIATION,deviation); } //--- Object name string Name(void) const { return this.GetProperty(GRAPH_OBJ_PROP_NAME); } void SetName(const string name) { if(CGBaseObj::Name()==name) return; if(CGBaseObj::Name()=="") { CGBaseObj::SetName(name); this.SetProperty(GRAPH_OBJ_PROP_NAME,name); return; } else { if(::ObjectSetString(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_NAME,name)) { CGBaseObj::SetName(name); this.SetProperty(GRAPH_OBJ_PROP_NAME,name); } } } //--- Object description (text contained in the object) string Text(void) const { return this.GetProperty(GRAPH_OBJ_PROP_TEXT); } void SetText(const string text) { if(::ObjectSetString(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_TEXT,text)) this.SetProperty(GRAPH_OBJ_PROP_TEXT,text); } //--- Tooltip text string Tooltip(void) const { return this.GetProperty(GRAPH_OBJ_PROP_TOOLTIP); } void SetTooltip(const string tooltip) { if(::ObjectSetString(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_TOOLTIP,tooltip)) this.SetProperty(GRAPH_OBJ_PROP_TOOLTIP,tooltip); } //--- Level description string LevelText(void) const { return this.GetProperty(GRAPH_OBJ_PROP_LEVELTEXT); } void SetLevelText(const string text) { if(::ObjectSetString(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_LEVELTEXT,text)) this.SetProperty(GRAPH_OBJ_PROP_LEVELTEXT,text); } //--- Font string Font(void) const { return this.GetProperty(GRAPH_OBJ_PROP_FONT); } void SetFont(const string font) { if(::ObjectSetString(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_FONT,font)) this.SetProperty(GRAPH_OBJ_PROP_FONT,font); } //--- BMP file name for the "Bitmap Level" object string BMPFile(void) const { return this.GetProperty(GRAPH_OBJ_PROP_BMPFILE); } void SetBMPFile(const string bmp_file) { if(::ObjectSetString(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_BMPFILE,bmp_file)) this.SetProperty(GRAPH_OBJ_PROP_BMPFILE,bmp_file); } //--- Symbol for the Chart object string Symbol(void) const { return this.GetProperty(GRAPH_OBJ_PROP_CHART_OBJ_SYMBOL); } void SetChartObjSymbol(const string symbol) { if(::ObjectSetString(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_SYMBOL,symbol)) this.SetProperty(GRAPH_OBJ_PROP_CHART_OBJ_SYMBOL,symbol); } }; //+------------------------------------------------------------------+
Viele Methoden sind hier im Vorfeld festgelegt worden. Später werden sie in die absteigenden Objektklassen mit entsprechenden Eigenschaften verschoben, um diese Klassen zu beschreiben. Daher werden die verschiedenen Objekte individuelle Methodensätze für die Arbeit mit Eigenschaften haben.
Betrachten wir die Logik anhand mehrerer Methoden als Beispiel.
Die dem Objekt innewohnenden Eigenschaften werden direkt von den Objekteigenschaften zurückgegeben und gesetzt:
//--- Object index in the list int Number(void) const { return (int)this.GetProperty(GRAPH_OBJ_PROP_NUM); } void SetNumber(const int number) { this.SetProperty(GRAPH_OBJ_PROP_NUM,number); }
Die Eigenschaften, die allen grafischen Objekten innewohnen und deren Speichervariablen sich in der grafischen Basisobjektklasse für alle grafischen Bibliotheksobjekte befinden, werden aus den Objekteigenschaften zurückgegeben und erst im Basisobjekt gesetzt und dann in den Objekteigenschaften:
//--- Object ID long ObjectID(void) const { return this.GetProperty(GRAPH_OBJ_PROP_ID); } void SetObjectID(const long obj_id) { CGBaseObj::SetObjectID(obj_id); this.SetProperty(GRAPH_OBJ_PROP_ID,obj_id); }
Die Eigenschaften, die einem grafischen Objekt innewohnen, aber nicht im Basisobjekt vorhanden sind, werden direkt von den Objekteigenschaften zurückgegeben und zuerst in den grafischen Objekteigenschaften gesetzt. Wenn das Eigenschaftsänderungsereignis erfolgreich in die Warteschlange gestellt wird, werden sie auch in den Objekteigenschaften gesetzt:
//--- Time coordinate datetime Time(void) const { return (datetime)this.GetProperty(GRAPH_OBJ_PROP_TIME); } void SetTime(const datetime time) { if(::ObjectSetInteger(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_TIME,time)) this.SetProperty(GRAPH_OBJ_PROP_TIME,time); }
Die Methode zum Setzen des Namens unterscheidet sich von anderen ähnlichen Methoden. Grafische Objekte werden im Terminal über den Listenindex und den Objektnamen ausgewählt (die Funktion Objektname() wird verwendet, um den Objektnamen über einen Index in der Objektliste zu erhalten, während die Funktionen ObjectGetXXX() dann verwendet werden, um die restlichen Eigenschaften über einen grafischen Objektnamen zu erhalten). Der Objektname wird ihm sofort bei der Erstellung zugewiesen.
Dementsprechend müssen wir hier den Namen nur auf Objektvariablen setzen. Wir tun dies nur, wenn der Name noch nicht in der Variablen gesetzt ist. Wenn der Name bereits in der Variablen gesetzt wurde und der zu setzende Name nicht mit dem bestehenden übereinstimmt (im Falle einer Übereinstimmung, verlasse die Methode), bedeutet dies eine Umbenennung des Objekts. Hier wird ein solcher Fall noch nicht behandelt. Im Moment senden wir einfach eine Anfrage zur Umbenennung eines grafischen Objekts und schreiben seinen Namen neu in die Basisklassenvariable und in die Eigenschaften des aktuellen Objekts.//--- Object name string Name(void) const { return this.GetProperty(GRAPH_OBJ_PROP_NAME); } void SetName(const string name) { if(CGBaseObj::Name()==name) return; if(CGBaseObj::Name()=="") { CGBaseObj::SetName(name); this.SetProperty(GRAPH_OBJ_PROP_NAME,name); return; } else { if(::ObjectSetString(CGBaseObj::ChartID(),CGBaseObj::Name(),OBJPROP_NAME,name)) { CGBaseObj::SetName(name); this.SetProperty(GRAPH_OBJ_PROP_NAME,name); } } }
Im geschützten parametrischen Konstruktor setzen wir alle dem Konstruktor übergebenen Werte auf die Eigenschaften der Basisklasse und des Objekts:
//+------------------------------------------------------------------+ //| Protected parametric constructor | //+------------------------------------------------------------------+ CGStdGraphObj::CGStdGraphObj(const ENUM_OBJECT_DE_TYPE obj_type,const ENUM_GRAPH_OBJ_BELONG belong,const long chart_id,const string name) { //--- Set the object (1) type, type of graphical (2) object, (3) element, (4) subwindow affiliation and (5) index, as well as (6) chart symbol Digits this.m_type=obj_type; CGBaseObj::SetChartID(chart_id); CGBaseObj::SetTypeGraphObject(CGBaseObj::GraphObjectType(obj_type)); CGBaseObj::SetTypeElement(GRAPH_ELEMENT_TYPE_STANDART); CGBaseObj::SetBelong(belong); CGBaseObj::SetSubwindow(chart_id,name); CGBaseObj::SetDigits((int)::SymbolInfoInteger(::ChartSymbol(chart_id),SYMBOL_DIGITS)); //--- Save integer properties //--- properties inherent in all graphical objects but not present in a graphical object this.m_long_prop[GRAPH_OBJ_PROP_CHART_ID] = CGBaseObj::ChartID(); // Chart ID this.m_long_prop[GRAPH_OBJ_PROP_WND_NUM] = CGBaseObj::SubWindow(); // Chart subwindow index this.m_long_prop[GRAPH_OBJ_PROP_TYPE] = CGBaseObj::TypeGraphObject(); // Graphical object type (ENUM_OBJECT) this.m_long_prop[GRAPH_OBJ_PROP_ELEMENT_TYPE]= CGBaseObj::TypeGraphElement(); // Graphical element type (ENUM_GRAPH_ELEMENT_TYPE) this.m_long_prop[GRAPH_OBJ_PROP_BELONG] = CGBaseObj::Belong(); // Graphical object affiliation this.m_long_prop[GRAPH_OBJ_PROP_ID] = 0; // Object ID this.m_long_prop[GRAPH_OBJ_PROP_NUM] = 0; // Object index in the list //--- Properties inherent in all graphical objects and present in a graphical object this.m_long_prop[GRAPH_OBJ_PROP_CREATETIME] = ::ObjectGetInteger(chart_id,name,OBJPROP_CREATETIME); // Object creation time this.m_long_prop[GRAPH_OBJ_PROP_TIMEFRAMES] = ::ObjectGetInteger(chart_id,name,OBJPROP_TIMEFRAMES); // Object visibility on timeframes this.m_long_prop[GRAPH_OBJ_PROP_BACK] = ::ObjectGetInteger(chart_id,name,OBJPROP_BACK); // Background object this.m_long_prop[GRAPH_OBJ_PROP_ZORDER] = ::ObjectGetInteger(chart_id,name,OBJPROP_ZORDER); // Priority of a graphical object for receiving the event of clicking on a chart this.m_long_prop[GRAPH_OBJ_PROP_HIDDEN] = ::ObjectGetInteger(chart_id,name,OBJPROP_HIDDEN); // Disable displaying the name of a graphical object in the terminal object list this.m_long_prop[GRAPH_OBJ_PROP_SELECTED] = ::ObjectGetInteger(chart_id,name,OBJPROP_SELECTED); // Object selection this.m_long_prop[GRAPH_OBJ_PROP_SELECTABLE] = ::ObjectGetInteger(chart_id,name,OBJPROP_SELECTABLE); // Object availability this.m_long_prop[GRAPH_OBJ_PROP_TIME] = ::ObjectGetInteger(chart_id,name,OBJPROP_TIME); // First point time coordinate this.m_long_prop[GRAPH_OBJ_PROP_COLOR] = ::ObjectGetInteger(chart_id,name,OBJPROP_COLOR); // Color this.m_long_prop[GRAPH_OBJ_PROP_STYLE] = ::ObjectGetInteger(chart_id,name,OBJPROP_STYLE); // Style this.m_long_prop[GRAPH_OBJ_PROP_WIDTH] = ::ObjectGetInteger(chart_id,name,OBJPROP_WIDTH); // Line width //--- Properties belonging to different graphical objects this.m_long_prop[GRAPH_OBJ_PROP_FILL] = 0; // Object color filling this.m_long_prop[GRAPH_OBJ_PROP_READONLY] = 0; // Ability to edit text in the Edit object this.m_long_prop[GRAPH_OBJ_PROP_LEVELS] = 0; // Number of levels this.m_long_prop[GRAPH_OBJ_PROP_LEVELCOLOR] = 0; // Level line color this.m_long_prop[GRAPH_OBJ_PROP_LEVELSTYLE] = 0; // Level line style this.m_long_prop[GRAPH_OBJ_PROP_LEVELWIDTH] = 0; // Level line width this.m_long_prop[GRAPH_OBJ_PROP_ALIGN] = 0; // Horizontal text alignment in the Edit object (OBJ_EDIT) this.m_long_prop[GRAPH_OBJ_PROP_FONTSIZE] = 0; // Font size this.m_long_prop[GRAPH_OBJ_PROP_RAY_LEFT] = 0; // Ray goes to the left this.m_long_prop[GRAPH_OBJ_PROP_RAY_RIGHT] = 0; // Ray goes to the right this.m_long_prop[GRAPH_OBJ_PROP_RAY] = 0; // Vertical line goes through all windows of a chart this.m_long_prop[GRAPH_OBJ_PROP_ELLIPSE] = 0; // Display the full ellipse of the Fibonacci Arc object this.m_long_prop[GRAPH_OBJ_PROP_ARROWCODE] = 0; // Arrow code for the "Arrow" object this.m_long_prop[GRAPH_OBJ_PROP_ANCHOR] = 0; // Position of the binding point of the graphical object this.m_long_prop[GRAPH_OBJ_PROP_XDISTANCE] = 0; // Distance from the base corner along the X axis in pixels this.m_long_prop[GRAPH_OBJ_PROP_YDISTANCE] = 0; // Distance from the base corner along the Y axis in pixels this.m_long_prop[GRAPH_OBJ_PROP_DIRECTION] = 0; // Gann object trend this.m_long_prop[GRAPH_OBJ_PROP_DEGREE] = 0; // Elliott wave marking level this.m_long_prop[GRAPH_OBJ_PROP_DRAWLINES] = 0; // Display lines for Elliott wave marking this.m_long_prop[GRAPH_OBJ_PROP_STATE] = 0; // Button state (pressed/released) this.m_long_prop[GRAPH_OBJ_PROP_OBJ_CHART_ID] = 0; // Chart object ID (OBJ_CHART). this.m_long_prop[GRAPH_OBJ_PROP_CHART_OBJ_PERIOD] = 0; // Chart object period< this.m_long_prop[GRAPH_OBJ_PROP_CHART_OBJ_DATE_SCALE] = 0; // Time scale display flag for the Chart object this.m_long_prop[GRAPH_OBJ_PROP_CHART_OBJ_PRICE_SCALE] = 0; // Price scale display flag for the Chart object this.m_long_prop[GRAPH_OBJ_PROP_CHART_OBJ_CHART_SCALE] = 0; // Chart object scale this.m_long_prop[GRAPH_OBJ_PROP_XSIZE] = 0; // Object width along the X axis in pixels. this.m_long_prop[GRAPH_OBJ_PROP_YSIZE] = 0; // Object height along the Y axis in pixels. this.m_long_prop[GRAPH_OBJ_PROP_XOFFSET] = 0; // X coordinate of the upper-left corner of the visibility area. this.m_long_prop[GRAPH_OBJ_PROP_YOFFSET] = 0; // Y coordinate of the upper-left corner of the visibility area. this.m_long_prop[GRAPH_OBJ_PROP_BGCOLOR] = 0; // Background color for OBJ_EDIT, OBJ_BUTTON, OBJ_RECTANGLE_LABEL this.m_long_prop[GRAPH_OBJ_PROP_CORNER] = 0; // Chart corner for binding a graphical object this.m_long_prop[GRAPH_OBJ_PROP_BORDER_TYPE] = 0; // Border type for "Rectangle border" this.m_long_prop[GRAPH_OBJ_PROP_BORDER_COLOR] = 0; // Border color for OBJ_EDIT and OBJ_BUTTON //--- Save real properties this.m_double_prop[this.IndexProp(GRAPH_OBJ_PROP_PRICE)] = ::ObjectGetDouble(chart_id,name,OBJPROP_PRICE); // Price coordinate this.m_double_prop[this.IndexProp(GRAPH_OBJ_PROP_LEVELVALUE)] = 0; // Level value this.m_double_prop[this.IndexProp(GRAPH_OBJ_PROP_SCALE)] = 0; // Scale (property of Gann objects and Fibonacci Arcs objects) this.m_double_prop[this.IndexProp(GRAPH_OBJ_PROP_ANGLE)] = 0; // Angle this.m_double_prop[this.IndexProp(GRAPH_OBJ_PROP_DEVIATION)] = 0; // Deviation of the standard deviation channel //--- Save string properties this.m_string_prop[this.IndexProp(GRAPH_OBJ_PROP_NAME)] = name; // Object name this.m_string_prop[this.IndexProp(GRAPH_OBJ_PROP_TEXT)] = ::ObjectGetString(chart_id,name,OBJPROP_TEXT); // Object description (the text contained in the object) this.m_string_prop[this.IndexProp(GRAPH_OBJ_PROP_TOOLTIP)] = ::ObjectGetString(chart_id,name,OBJPROP_TOOLTIP);// Tooltip text this.m_string_prop[this.IndexProp(GRAPH_OBJ_PROP_LEVELTEXT)] = ""; // Level description this.m_string_prop[this.IndexProp(GRAPH_OBJ_PROP_FONT)] = ""; // Font this.m_string_prop[this.IndexProp(GRAPH_OBJ_PROP_BMPFILE)] = ""; // BMP file name for the "Bitmap Level" object this.m_string_prop[this.IndexProp(GRAPH_OBJ_PROP_CHART_OBJ_SYMBOL)]= ""; // Chart object symbol //--- Save basic properties in the parent object this.m_create_time=(datetime)this.GetProperty(GRAPH_OBJ_PROP_CREATETIME); this.m_back=(bool)this.GetProperty(GRAPH_OBJ_PROP_BACK); this.m_selected=(bool)this.GetProperty(GRAPH_OBJ_PROP_SELECTED); this.m_selectable=(bool)this.GetProperty(GRAPH_OBJ_PROP_SELECTABLE); this.m_hidden=(bool)this.GetProperty(GRAPH_OBJ_PROP_HIDDEN); this.m_name=this.GetProperty(GRAPH_OBJ_PROP_NAME); } //+-------------------------------------------------------------------+
Die Reihenfolge des Setzens von Werten in Objektvariablen ist in den Codekommentaren beschrieben. Wir setzen nicht jede Objekteigenschaft, sondern nur die Eigenschaften, die an den Konstruktor übergeben werden, und die, die wir vom grafischen Objekt erhalten können, sofern sie für alle grafischen Objekte gleich sind. Alle übrigen Eigenschaften sind in den Konstruktoren der Nachfolgeklassen zu setzen, da jedes grafische Objekt über unterschiedliche Eigenschaftssätze verfügt, die erst bei der Erstellung eines bestimmten grafischen Objekts bekannt werden.
Standardmethoden für den Vergleich zweier Objekte:
//+-----------------------------------------------------------------------+ //|Compare CGStdGraphObj objects with each other by the specified property| //+-----------------------------------------------------------------------+ int CGStdGraphObj::Compare(const CObject *node,const int mode=0) const { const CGStdGraphObj *obj_compared=node; //--- compare integer properties of two orders if(mode<GRAPH_OBJ_PROP_INTEGER_TOTAL) { long value_compared=obj_compared.GetProperty((ENUM_GRAPH_OBJ_PROP_INTEGER)mode); long value_current=this.GetProperty((ENUM_GRAPH_OBJ_PROP_INTEGER)mode); return(value_current>value_compared ? 1 : value_current<value_compared ? -1 : 0); } //--- compare real properties of two orders else if(mode<GRAPH_OBJ_PROP_DOUBLE_TOTAL+GRAPH_OBJ_PROP_INTEGER_TOTAL) { double value_compared=obj_compared.GetProperty((ENUM_GRAPH_OBJ_PROP_DOUBLE)mode); double value_current=this.GetProperty((ENUM_GRAPH_OBJ_PROP_DOUBLE)mode); return(value_current>value_compared ? 1 : value_current<value_compared ? -1 : 0); } //--- compare string properties of two orders else if(mode<GRAPH_OBJ_PROP_DOUBLE_TOTAL+GRAPH_OBJ_PROP_INTEGER_TOTAL+GRAPH_OBJ_PROP_STRING_TOTAL) { string value_compared=obj_compared.GetProperty((ENUM_GRAPH_OBJ_PROP_STRING)mode); string value_current=this.GetProperty((ENUM_GRAPH_OBJ_PROP_STRING)mode); return(value_current>value_compared ? 1 : value_current<value_compared ? -1 : 0); } return 0; } //+------------------------------------------------------------------+ //| Compare CGStdGraphObj objects by all properties | //+------------------------------------------------------------------+ bool CGStdGraphObj::IsEqual(CGStdGraphObj *compared_obj) const { int beg=0, end=GRAPH_OBJ_PROP_INTEGER_TOTAL; for(int i=beg; i<end; i++) { ENUM_GRAPH_OBJ_PROP_INTEGER prop=(ENUM_GRAPH_OBJ_PROP_INTEGER)i; if(this.GetProperty(prop)!=compared_obj.GetProperty(prop)) return false; } beg=end; end+=GRAPH_OBJ_PROP_DOUBLE_TOTAL; for(int i=beg; i<end; i++) { ENUM_GRAPH_OBJ_PROP_DOUBLE prop=(ENUM_GRAPH_OBJ_PROP_DOUBLE)i; if(this.GetProperty(prop)!=compared_obj.GetProperty(prop)) return false; } beg=end; end+=GRAPH_OBJ_PROP_STRING_TOTAL; for(int i=beg; i<end; i++) { ENUM_GRAPH_OBJ_PROP_STRING prop=(ENUM_GRAPH_OBJ_PROP_STRING)i; if(this.GetProperty(prop)!=compared_obj.GetProperty(prop)) return false; } return true; } //+------------------------------------------------------------------+
Die Methode, die Objekteigenschaften im Journal anzeigt:
//+------------------------------------------------------------------+ //| Display object properties in the journal | //+------------------------------------------------------------------+ void CGStdGraphObj::Print(const bool full_prop=false,const bool dash=false) { ::Print("============= ",CMessage::Text(MSG_LIB_PARAMS_LIST_BEG)," (",this.Header(),") ============="); int beg=0, end=GRAPH_OBJ_PROP_INTEGER_TOTAL; for(int i=beg; i<end; i++) { ENUM_GRAPH_OBJ_PROP_INTEGER prop=(ENUM_GRAPH_OBJ_PROP_INTEGER)i; if(!full_prop && !this.SupportProperty(prop)) continue; ::Print(this.GetPropertyDescription(prop)); } ::Print("------"); beg=end; end+=GRAPH_OBJ_PROP_DOUBLE_TOTAL; for(int i=beg; i<end; i++) { ENUM_GRAPH_OBJ_PROP_DOUBLE prop=(ENUM_GRAPH_OBJ_PROP_DOUBLE)i; if(!full_prop && !this.SupportProperty(prop)) continue; ::Print(this.GetPropertyDescription(prop)); } ::Print("------"); beg=end; end+=GRAPH_OBJ_PROP_STRING_TOTAL; for(int i=beg; i<end; i++) { ENUM_GRAPH_OBJ_PROP_STRING prop=(ENUM_GRAPH_OBJ_PROP_STRING)i; if(!full_prop && !this.SupportProperty(prop)) continue; ::Print(this.GetPropertyDescription(prop)); } ::Print("============= ",CMessage::Text(MSG_LIB_PARAMS_LIST_END)," (",this.Header(),") =============\n"); } //+------------------------------------------------------------------+
Die Methode gibt einen kurzen Objektnamen zurück:
//+------------------------------------------------------------------+ //| Return the object short name | //+------------------------------------------------------------------+ string CGStdGraphObj::Header(const bool symbol=false) { return CGBaseObj::TypeGraphObjectDescription(); } //+------------------------------------------------------------------+
Die Methode zeigt die kurze Objektbeschreibung im Journal an:
//+------------------------------------------------------------------+ //| Display a short description of the object in the journal | //+------------------------------------------------------------------+ void CGStdGraphObj::PrintShort(const bool dash=false,const bool symbol=false) { ::Print ( this.Header(symbol)," \"",CGBaseObj::Name(),"\": ID ",(string)this.GetProperty(GRAPH_OBJ_PROP_ID), " ",::TimeToString(CGBaseObj::TimeCreate(),TIME_DATE|TIME_MINUTES|TIME_SECONDS) ); } //+------------------------------------------------------------------+
Die Methode zur Rückgabe der Objekteigenschaftsbeschreibung mit den Typen Ganzzahl, Reell und Text:
//+------------------------------------------------------------------+ //| Return description of object's integer property | //+------------------------------------------------------------------+ string CGStdGraphObj::GetPropertyDescription(ENUM_GRAPH_OBJ_PROP_INTEGER property) { return ( property==GRAPH_OBJ_PROP_ID ? CMessage::Text(MSG_GRAPH_OBJ_PROP_ID)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_TYPE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_TYPE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+StdGraphObjectTypeDescription((ENUM_OBJECT)this.GetProperty(property)) ) : property==GRAPH_OBJ_PROP_ELEMENT_TYPE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_ELEMENT_TYPE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+CGBaseObj::TypeElementDescription() ) : property==GRAPH_OBJ_PROP_BELONG ? CMessage::Text(MSG_GRAPH_OBJ_PROP_BELONG)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+CGBaseObj::BelongDescription() ) : property==GRAPH_OBJ_PROP_CHART_ID ? CMessage::Text(MSG_GRAPH_OBJ_PROP_CHART_ID)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_WND_NUM ? CMessage::Text(MSG_GRAPH_OBJ_PROP_WND_NUM)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_CREATETIME ? CMessage::Text(MSG_GRAPH_OBJ_PROP_CREATETIME)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::TimeToString(this.GetProperty(property),TIME_DATE|TIME_MINUTES|TIME_SECONDS) ) : property==GRAPH_OBJ_PROP_TIMEFRAMES ? CMessage::Text(MSG_GRAPH_OBJ_PROP_TIMEFRAMES)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_BACK ? CMessage::Text(MSG_GRAPH_OBJ_PROP_BACK)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.IsBack() ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_ZORDER ? CMessage::Text(MSG_GRAPH_OBJ_PROP_ZORDER)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_HIDDEN ? CMessage::Text(MSG_GRAPH_OBJ_PROP_HIDDEN)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.IsHidden() ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_SELECTED ? CMessage::Text(MSG_GRAPH_OBJ_PROP_SELECTED)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.IsSelected() ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_SELECTABLE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_SELECTABLE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.IsSelectable() ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_NUM ? CMessage::Text(MSG_GRAPH_OBJ_PROP_NUM)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_TIME ? CMessage::Text(MSG_GRAPH_OBJ_PROP_TIME)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::TimeToString(this.GetProperty(property),TIME_DATE|TIME_MINUTES) ) : property==GRAPH_OBJ_PROP_COLOR ? CMessage::Text(MSG_GRAPH_OBJ_PROP_COLOR)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::ColorToString((color)this.GetProperty(property),true) ) : property==GRAPH_OBJ_PROP_STYLE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_STYLE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+LineStyleDescription((ENUM_LINE_STYLE)this.GetProperty(property)) ) : property==GRAPH_OBJ_PROP_WIDTH ? CMessage::Text(MSG_GRAPH_OBJ_PROP_WIDTH)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_FILL ? CMessage::Text(MSG_GRAPH_OBJ_PROP_FILL)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_READONLY ? CMessage::Text(MSG_GRAPH_OBJ_PROP_READONLY)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_LEVELS ? CMessage::Text(MSG_GRAPH_OBJ_PROP_LEVELS)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_LEVELCOLOR ? CMessage::Text(MSG_GRAPH_OBJ_PROP_LEVELCOLOR)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::ColorToString((color)this.GetProperty(property),true) ) : property==GRAPH_OBJ_PROP_LEVELSTYLE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_LEVELSTYLE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+LineStyleDescription((ENUM_LINE_STYLE)this.GetProperty(property)) ) : property==GRAPH_OBJ_PROP_LEVELWIDTH ? CMessage::Text(MSG_GRAPH_OBJ_PROP_LEVELWIDTH)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_ALIGN ? CMessage::Text(MSG_GRAPH_OBJ_PROP_ALIGN)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+AlignModeDescription((ENUM_ALIGN_MODE)this.GetProperty(property)) ) : property==GRAPH_OBJ_PROP_FONTSIZE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_FONTSIZE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_RAY_LEFT ? CMessage::Text(MSG_GRAPH_OBJ_PROP_RAY_LEFT)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_RAY_RIGHT ? CMessage::Text(MSG_GRAPH_OBJ_PROP_RAY_RIGHT)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_RAY ? CMessage::Text(MSG_GRAPH_OBJ_PROP_RAY)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_ELLIPSE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_ELLIPSE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_ARROWCODE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_ARROWCODE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_ANCHOR ? CMessage::Text(MSG_GRAPH_OBJ_PROP_ANCHOR)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+this.AnchorDescription() ) : property==GRAPH_OBJ_PROP_XDISTANCE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_XDISTANCE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_YDISTANCE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_YDISTANCE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_DIRECTION ? CMessage::Text(MSG_GRAPH_OBJ_PROP_DIRECTION)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+GannDirectDescription((ENUM_GANN_DIRECTION)this.GetProperty(property)) ) : property==GRAPH_OBJ_PROP_DEGREE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_DEGREE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+ElliotWaveDegreeDescription((ENUM_ELLIOT_WAVE_DEGREE)this.GetProperty(property)) ) : property==GRAPH_OBJ_PROP_DRAWLINES ? CMessage::Text(MSG_GRAPH_OBJ_PROP_DRAWLINES)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_STATE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_STATE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_BUTTON_STATE_PRESSED) : CMessage::Text(MSG_LIB_TEXT_BUTTON_STATE_DEPRESSED)) ) : property==GRAPH_OBJ_PROP_OBJ_CHART_ID ? CMessage::Text(MSG_CHART_OBJ_ID)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_CHART_OBJ_PERIOD ? CMessage::Text(MSG_GRAPH_OBJ_PROP_CHART_OBJ_PERIOD)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+TimeframeDescription((ENUM_TIMEFRAMES)this.GetProperty(property)) ) : property==GRAPH_OBJ_PROP_CHART_OBJ_DATE_SCALE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_CHART_OBJ_DATE_SCALE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_CHART_OBJ_PRICE_SCALE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_CHART_OBJ_PRICE_SCALE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(this.GetProperty(property) ? CMessage::Text(MSG_LIB_TEXT_YES) : CMessage::Text(MSG_LIB_TEXT_NO)) ) : property==GRAPH_OBJ_PROP_CHART_OBJ_CHART_SCALE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_CHART_OBJ_CHART_SCALE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_XSIZE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_XSIZE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_YSIZE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_YSIZE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_XOFFSET ? CMessage::Text(MSG_GRAPH_OBJ_PROP_XOFFSET)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_YOFFSET ? CMessage::Text(MSG_GRAPH_OBJ_PROP_YOFFSET)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+(string)this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_BGCOLOR ? CMessage::Text(MSG_GRAPH_OBJ_PROP_BGCOLOR)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::ColorToString((color)this.GetProperty(property),true) ) : property==GRAPH_OBJ_PROP_CORNER ? CMessage::Text(MSG_GRAPH_OBJ_PROP_CORNER)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+BaseCornerDescription((ENUM_BASE_CORNER)this.GetProperty(property)) ) : property==GRAPH_OBJ_PROP_BORDER_TYPE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_BORDER_TYPE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+BorderTypeDescription((ENUM_BORDER_TYPE)this.GetProperty(property)) ) : property==GRAPH_OBJ_PROP_BORDER_COLOR ? CMessage::Text(MSG_GRAPH_OBJ_PROP_BORDER_COLOR)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::ColorToString((color)this.GetProperty(property),true) ) : "" ); } //+------------------------------------------------------------------+ //| Return description of object's real property | //+------------------------------------------------------------------+ string CGStdGraphObj::GetPropertyDescription(ENUM_GRAPH_OBJ_PROP_DOUBLE property) { int dg=(this.m_digits>0 ? this.m_digits : 1); return ( property==GRAPH_OBJ_PROP_PRICE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_PRICE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::DoubleToString(this.GetProperty(property),dg) ) : property==GRAPH_OBJ_PROP_LEVELVALUE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_LEVELVALUE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::DoubleToString(this.GetProperty(property),dg) ) : property==GRAPH_OBJ_PROP_SCALE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_SCALE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::DoubleToString(this.GetProperty(property),2) ) : property==GRAPH_OBJ_PROP_ANGLE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_ANGLE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::DoubleToString(this.GetProperty(property),2) ) : property==GRAPH_OBJ_PROP_DEVIATION ? CMessage::Text(MSG_GRAPH_OBJ_PROP_DEVIATION)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+::DoubleToString(this.GetProperty(property),2) ) : "" ); } //+------------------------------------------------------------------+ //| Return description of object's string property | //+------------------------------------------------------------------+ string CGStdGraphObj::GetPropertyDescription(ENUM_GRAPH_OBJ_PROP_STRING property) { return ( property==GRAPH_OBJ_PROP_NAME ? CMessage::Text(MSG_GRAPH_OBJ_PROP_NAME)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_TEXT ? CMessage::Text(MSG_GRAPH_OBJ_PROP_TEXT)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_TOOLTIP ? CMessage::Text(MSG_GRAPH_OBJ_PROP_TOOLTIP)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_LEVELTEXT ? CMessage::Text(MSG_GRAPH_OBJ_PROP_LEVELTEXT)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_FONT ? CMessage::Text(MSG_GRAPH_OBJ_PROP_FONT)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_BMPFILE ? CMessage::Text(MSG_GRAPH_OBJ_PROP_BMPFILE)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+this.GetProperty(property) ) : property==GRAPH_OBJ_PROP_CHART_OBJ_SYMBOL ? CMessage::Text(MSG_GRAPH_OBJ_PROP_SYMBOL)+ (!this.SupportProperty(property) ? ": "+CMessage::Text(MSG_LIB_PROP_NOT_SUPPORTED) : ": "+this.GetProperty(property) ) : "" ); } //+------------------------------------------------------------------+
Die Arbeit der Methoden, die den oben vorgestellten ähnlich sind, wurde bereits zu Beginn der Bibliotheksbeschreibung berücksichtigt. Außerdem wurden im Laufe der Zeit beim Hinzufügen verschiedener Objekte einige Klarstellungen hinsichtlich ihrer Funktionslogik vorgenommen. Sie sollten Ihnen also an dieser Stelle vertraut sein. Wenn Sie Fragen haben, können Sie diese gerne im Kommentarteil unten stellen.
Ich habe die abstrakte grafische Objektklasse erstellt. Nun müssen wir die Tatsache, dass ein grafisches Objekt auf einem Chart erschienen ist, definieren und das entsprechende abstrakte, grafische Objekt in der Klasse der grafischen Objekte in der Kollektion erstellen.
Ich werde diese Objekte hier nicht in die Kollektionsliste aufnehmen. Wir brauchen abstrakte Objektnachfolger, die bestimmte Typen von grafischen Objekten beschreiben, die dem Chart hinzugefügt werden. Ich werde sie im nächsten Artikel implementieren. Hier werde ich nur prüfen, ob die neu erstellte Klasse korrekt funktioniert.
Ich werde einige Änderungen an der Chart-Objektverwaltungsklasse in \MQL5\Include\DoEasy\Collections\GraphElementsCollection.mqh vornehmen müssen. Es ist nicht möglich, eine ressourcensparende Berechnung für die Suche nach dem letzten grafischen Objekt, das dem Chart hinzugefügt wurde, zu erstellen, wie ich es bei anderen Kollektionen getan habe, bei denen die Schleife vom Index des letzten Objekts unter den von der Kollektionsklasse verwalteten Objekten aus gestartet wurde. Das ist nicht möglich, weil grafische Objekte nicht in der Reihenfolge, in der sie dem Chart hinzugefügt werden, sondern nach ihrem Namen in die Terminal-Liste aufgenommen werden. Merkwürdigerweise werden grafische Objekte in der Terminal-Liste nach Namen sortiert. Das zuletzt zum Chart hinzugefügte Pfeilsymbol steht in der Objektliste an erster Stelle, während das Rechteckobjekt aufgrund seines Namens an zweiter Stelle steht.
Daher müssen wir ein Objekt nach dem Zeitpunkt suchen, zu dem es dem Chart in der Schleife aller grafischen Chart-Objekte hinzugefügt wurde. Die Extravariable, die eine ressourcensparende Suche organisiert und der Klasse vorläufig hinzugefügt wurde, sowie die mit ihrer Hilfe durchgeführten Berechnungen sollten entfernt werden:
//+------------------------------------------------------------------+ //| GraphElementsCollection.mqh | //| Copyright 2021, MetaQuotes Ltd. | //| https://mql5.com/en/users/artmedia70 | //+------------------------------------------------------------------+ #property copyright "Copyright 2021, MetaQuotes Ltd." #property link "https://mql5.com/en/users/artmedia70" #property version "1.00" //+------------------------------------------------------------------+ //| Include files | //+------------------------------------------------------------------+ #include "ListObj.mqh" #include "..\Services\Select.mqh" #include "..\Objects\Graph\Form.mqh" //+------------------------------------------------------------------+ //| Chart object management class | //+------------------------------------------------------------------+ class CChartObjectsControl : public CObject { private: ENUM_TIMEFRAMES m_chart_timeframe; // Chart timeframe long m_chart_id; // Chart ID string m_chart_symbol; // Chart symbol bool m_is_graph_obj_event; // Event flag in the list of graphical objects int m_total_objects; // Number of graphical objects int m_last_objects; // Number of graphical objects during the previous check int m_index_object; // Index of the last graphical object added to the collection from the terminal object list int m_delta_graph_obj; // Difference in the number of graphical objects compared to the previous check public: //--- Return the variable values ENUM_TIMEFRAMES Timeframe(void) const { return this.m_chart_timeframe; } long ChartID(void) const { return this.m_chart_id; } string Symbol(void) const { return this.m_chart_symbol; } bool IsEvent(void) const { return this.m_is_graph_obj_event; } int TotalObjects(void) const { return this.m_total_objects; } int Delta(void) const { return this.m_delta_graph_obj; } //--- Check the chart objects void Refresh(void); //--- Constructors CChartObjectsControl(void) { this.m_chart_id=::ChartID(); this.m_chart_timeframe=(ENUM_TIMEFRAMES)::ChartPeriod(this.m_chart_id); this.m_chart_symbol=::ChartSymbol(this.m_chart_id); this.m_is_graph_obj_event=false; this.m_total_objects=0; this.m_last_objects=0; this.m_index_object=0; this.m_delta_graph_obj=0; } CChartObjectsControl(const long chart_id) { this.m_chart_id=chart_id; this.m_chart_timeframe=(ENUM_TIMEFRAMES)::ChartPeriod(this.m_chart_id); this.m_chart_symbol=::ChartSymbol(this.m_chart_id); this.m_is_graph_obj_event=false; this.m_total_objects=0; this.m_last_objects=0; this.m_index_object=0; this.m_delta_graph_obj=0; } //--- Compare CChartObjectsControl objects by a chart ID (for sorting the list by an object property) virtual int Compare(const CObject *node,const int mode=0) const { const CChartObjectsControl *obj_compared=node; return(this.ChartID()>obj_compared.ChartID() ? 1 : this.ChartID()<obj_compared.ChartID() ? -1 : 0); } }; //+------------------------------------------------------------------+ //| CChartObjectsControl Check objects on a chart | //+------------------------------------------------------------------+ void CChartObjectsControl::Refresh(void) { //--- Graphical objects on the chart this.m_total_objects=::ObjectsTotal(this.ChartID()); int i=this.m_index_object; int delta=this.m_total_objects-this.m_last_objects; //--- If the number of objects has changed if(delta!=0) {
Die Methode zur Überprüfung von Chart-Objekten erhält das Handle zur Erhöhung der Anzahl der grafischen Objekte auf dem Chart:
//+------------------------------------------------------------------+ //| CChartObjectsControl Check objects on a chart | //+------------------------------------------------------------------+ void CChartObjectsControl::Refresh(void) { //--- Graphical objects on the chart this.m_total_objects=::ObjectsTotal(this.ChartID()); this.m_delta_graph_obj=this.m_total_objects-this.m_last_objects; //--- If the number of objects has changed if(this.m_delta_graph_obj!=0) { //--- Create the string and display it in the journal with the chart ID, its symbol and timeframe string txt=", "+(m_delta_graph_obj>0 ? "Added: " : "Deleted: ")+(string)fabs(m_delta_graph_obj)+" obj"; Print(DFUN,"ChartID=",this.ChartID(),", ",this.Symbol(),", ",TimeframeDescription(this.Timeframe()),txt); } //--- If an object is added to the chart if(this.m_delta_graph_obj>0) { int index=0; datetime time=0; string name=""; //--- find the last added graphical object and write its index for(int j=0;j<this.m_total_objects;j++) { name=::ObjectName(this.ChartID(),j); datetime tm=(datetime)::ObjectGetInteger(this.ChartID(),name,OBJPROP_CREATETIME); if(tm>time) { time=tm; index=j; } } //--- Select the last graphical object by its index name=::ObjectName(this.ChartID(),index); if(name!="") { //--- Create the object of the abstract graphical object class ENUM_OBJECT type=(ENUM_OBJECT)::ObjectGetInteger(this.ChartID(),name,OBJPROP_TYPE); ENUM_OBJECT_DE_TYPE obj_type=ENUM_OBJECT_DE_TYPE(type+OBJECT_DE_TYPE_GSTD_OBJ+1); CGStdGraphObj *obj=new CGStdGraphObj(obj_type,GRAPH_OBJ_BELONG_NO_PROGRAM,this.ChartID(),name); if(obj!=NULL) { //--- Set the object index, display its short description and remove the created object obj.SetObjectID(this.m_total_objects); obj.PrintShort(); delete obj; } } } //--- save the index of the last added graphical object and the difference with the last check this.m_last_objects=this.m_total_objects; this.m_is_graph_obj_event=(bool)this.m_delta_graph_obj; } //+------------------------------------------------------------------+
Die Hauptlogik ist in den Kommentaren zum Code beschrieben.
Abschließend und um ein langjähriges Versäumnis zu korrigieren, erhält der Klassendestruktor der Hauptobjektklasse der CEngine-Bibliothek in \MQL5\Include\DoEasy\Engine.mqh die Möglichkeit, alle im Chart vorhandenen Kommentare zu löschen:
//+------------------------------------------------------------------+ //| CEngine destructor | //+------------------------------------------------------------------+ CEngine::~CEngine() { ::EventKillTimer(); ::Comment(""); } //+------------------------------------------------------------------+
Nun ist es an der Zeit, die neu erstellte Funktionalität zu testen.
Test
Um den Test durchzuführen, verwenden wir den EA aus dem vorherigen Artikel und speichern ihn in \MQL5\Experts\TestDoEasy\Part83\ als TestDoEasyPart83.mq5.
Das mag seltsam erscheinen, aber wir müssen keine Änderungen an der EA-Logik vornehmen. Ich werde nur das Verhalten in der Funktion OnDeinit() leicht ändern:
//+------------------------------------------------------------------+ //| Expert deinitialization function | //+------------------------------------------------------------------+ void OnDeinit(const int reason) { //--- destroy timer EventKillTimer(); Comment(""); } //+------------------------------------------------------------------+
Anstatt den Millisekunden-Timer zu zerstören und alle Chart-Kommentare zu löschen, fügen wir den Aufruf der gleichnamigen Bibliotheksmethode hinzu:
//+------------------------------------------------------------------+ //| Expert deinitialization function | //+------------------------------------------------------------------+ void OnDeinit(const int reason) { //--- Deinitialize library engine.OnDeinit(); } //+------------------------------------------------------------------+
Beim Versuch, den EA zu kompilieren, tritt folgender Fehler auf:
'CGStdGraphObj::CGStdGraphObj' - cannot access protected member function
see declaration of 'CGStdGraphObj::CGStdGraphObj'
1 errors, 0 warnings
Dies ist zu erwarten, da der parametrische Konstruktor der abstrakten grafischen Objektklasse im privaten Klassenbereich deklariert ist. Um den Fehler zu beheben, setzen wir vorübergehend den Zugriffsrestriktion 'public' für den Konstruktor:
//--- Default constructor CGStdGraphObj(){ this.m_type=OBJECT_DE_TYPE_GSTD_OBJ; } protected: public: //--- Protected parametric constructor CGStdGraphObj(const ENUM_OBJECT_DE_TYPE obj_type,const ENUM_GRAPH_OBJ_BELONG belong,const long chart_id,const string name);
Kompilieren Sie den EA neu und starten Sie ihn.
Verschiedene grafische Objekte werden dem Chart hinzugefügt, während das Journal Meldungen über das Hinzufügen eines neuen Objekts zusammen mit einer kurzen Beschreibung anzeigt:
Wie wir sehen können, funktioniert alles wie erwartet.
Was kommt als Nächstes?
Im nächsten Artikel werde ich die Klassen der grafischen Standardobjekte erstellen und die Verfeinerung der Kollektion grafischer Objekte fortsetzen.
Ihre Fragen und Vorschläge schreiben Sie bitte in den Kommentarteil.
*Frühere Artikel dieser Serie:
Grafiken in der Bibliothek DoEasy (Teil 73): Das Formularobjekt eines grafischen Elements
Grafiken in der Bibliothek DoEasy (Teil 74): Das grafisches Basiselement, das von der Klasse CCanvas unterstützt wird
Grafiken in der Bibliothek DoEasy (Teil 75): Methoden zur Handhabung von Primitiven und Text im grafischen Grundelement
Grafiken in der Bibliothek DoEasy (Teil 76): Das Formularobjekt und vordefinierte Farbschemata
Grafik in der Bibliothek DoEasy (Teil 77): Objektklasse der Schatten
Grafik in der Bibliothek DoEasy (Teil 78): Animationsprinzipien in der Bibliothek. Schneiden von Bildern
Grafik in der Bibliothek DoEasy (Teil 79): Die Objektklasse "Animationsrahmen" und ihre abgeleiteten Objekte
Grafik in der Bibliothek DoEasy (Teil 80): Die Objektklasse "Geometrischer Animationsrahmen"
Grafik in der Bibliothek DoEasy (Teil 81): Integration von Grafiken in Bibliotheksobjekt
Grafiken in der Bibliothek DoEasy (Teil 82): Die Umgestaltung von Bibliotheksobjekten und Kollektion von grafischen Objekten
Übersetzt aus dem Russischen von MetaQuotes Ltd.
Originalartikel: https://www.mql5.com/ru/articles/9902
- Freie Handelsapplikationen
- Über 8.000 Signale zum Kopieren
- Wirtschaftsnachrichten für die Lage an den Finanzmärkte
Sie stimmen der Website-Richtlinie und den Nutzungsbedingungen zu.