Создание графической библиотеки с нуля - страница 3

 
Maxim Kuznetsov:

Кратко, про инженерию :

если есть позыв улучшить некое "А" методом повторной разработки, надо конкретизировать его критические недостатки. Просто их перечислить и объяснить почему это неустранимо в процессе эволюционного развития "А".

с другой стороны, никто-же не запрещает. Нравится писать код, пиши... Перепишешь "А", но по своему, зато оно будет новое

Макс, привет!

Ну я уже неоднократно описывал "недостатки", которые с моей точки зрения я вижу в стандартной библиотеке и в библиотеке Анатолия.

У обеих библиотек есть один существенный, на мой взгляд, недостаток: интерфейс строится на дискретных объектах чарта, То есть чем больше элементов управления в интерфейсе, тем больше обособленных объектов на самом графике. С одной стороны это вроде как само по себе не представляет проблемы, а с другой стороны это представляет проблему при перетаскивании диалогов, так как перетаскивается не единый объект "форма с элементами", а множество различных элементов. А на это расходуются дополнительные ресурсы.

Библиотека Анатолия очень шикарна, но она сложна по своему составу и сложна в интеграции в основную программу. А стандартная библиотека ограничена в самих элементах управления, хотя исходная архитектура очень даже хорошая на мой взгляд.

По сути лучшим решением было бы то, что пытается сделать Петр Конов: графический конструктор создания интерфейсов с генерацией кода GUI, но только с расширенной событийной моделью, чтобы при интеграции с основной программой не приходилось лазить в огромный код GUI (что-то вроде аналога MVVM), ну и конечно же с объектами, которые пользователи могли бы самостоятельно расширять.

 
Алексей Барбашин:

Макс, привет!

Ну я уже неоднократно описывал "недостатки", которые с моей точки зрения я вижу в стандартной библиотеке и в библиотеке Анатолия.

У обеих библиотек есть один существенный, на мой взгляд, недостаток: интерфейс строится на дискретных объектах чарта, То есть чем больше элементов управления в интерфейсе, тем больше обособленных объектов на самом графике. С одной стороны это вроде как само по себе не представляет проблемы, а с другой стороны это представляет проблему при перетаскивании диалогов, так как перетаскивается не единый объект "форма с элементами", а множество различных элементов. А на это расходуются дополнительные ресурсы.

Библиотека Анатолия очень шикарна, но она сложна по своему составу и сложна в интеграции в основную программу. А стандартная библиотека ограничена в самих элементах управления, хотя исходная архитектура очень даже хорошая на мой взгляд.

По сути лучшим решением было бы то, что пытается сделать Петр Конов: графический конструктор создания интерфейсов с генерацией кода GUI, но только с расширенной событийной моделью, чтобы при интеграции с основной программой не приходилось лазить в огромный код GUI, ну и конечно же с объектами, которые пользователи могли бы самостоятельно расширять.

цитату правильно читать снизу-вверх. Внизу (то что подчёркнуто) более важное. Оно вообще определяющее

довольно удивительно, при всём современном развитии всех Human Interface, видеть что во главу ставятся  представления координат и элементы форм.
При этом все спокойно пользуются броузерами c Rest/Ajax, в курсе что такое MVC но про интерфейс между советником и его GUI не задумываются.

если модель описана и есть протокол как с ней работать, то GUI может быть любой и не будет зависть от советника. Директивно вбивать окошки в советник, это какое-то злое-злое-зло. У советников основная задача это торговать, всё прочее должно быть вынесено из основного кода и быть опциональным.

 
Maxim Kuznetsov:

цитату правильно читать снизу-вверх. Внизу (то что подчёркнуто) более важное. Оно вообще определяющее

довольно удивительно, при всём современном развитии всех Human Interface, видеть что во главу ставятся  представления координат и элементы форм.
При этом все спокойно пользуются броузерами c Rest/Ajax, в курсе что такое MVC но про интерфейс между советником и его GUI не задумываются.

если модель описана и есть протокол как с ней работать, то GUI может быть любой и не будет зависть от советника. Директивно вбивать окошки в советник, это какое-то злое-злое-зло. У советников основная задача это торговать, всё прочее должно быть вынесено из основного кода и быть опциональным.

Полагаю что тут стоит исходить из того, что изначально разработчики не задумывались над тем, что может потребоваться функциональность интерфейсов. Если ты помнишь, то на ранних стадиях не было даже никакого ООП в mql, его основное предназначение скатывалось только к написанию индикаторов и все было под это заточено.

А сегодня мы наблюдаем что метаквоты уже работают и с сокетами и с базами данных, причем на уровне самого ядра программы... А механизмы взаимодействия между пользователем и программой так и остались в стороне.

При этом сами разработчики почти десять лет назад заявили что разработка интерфейсов является очень важным механизмом взаимодействия между пользователем и приложением и разработали под это дело стандартную библиотеку, но вот только ее применимость под задачи не показали и по сути даже на сегодняшний день очень многие программисты не знают о ее существовании.

Будем стараться устранять пробелы. Даже если это не потребуется другим участникам, определенный опыт все равно будет приобретен.

 
Alexandr Andreev:

Начал именно с Вашей библиотеки, за что спасибо, потом немного причесал, потом еще, потом еще))) изменил в итоге все включая переписанных функций линий, также функцию широкой линии это из исходника канваса , убрал фейковые функции, поставил заглушку на эвент.   еще не полностью ушел от структуры W хотя там тоже мало чего осталось. Добавил вычисление бара с лева и справа по бинарному поиску среди сторонних элементов, соответственно добавил сам бинарный поиск двухсторонний с возможность выбора большего или меньшего значения. Также добавил возможность построения от массивов любого вида (таймсерия/обычный ) И пришел к вывод что надо менять конструкцию))))))

Классно.

Да, библиотеки должны быть или универсальные для начинающих программеров, или узконаправленными уже для более продвинутых.

У самого несколько версий моего же iCanvas для разных целей.

Поэтому и заговорил о формулировки списка намерений и целей или хотябы обозначить направление. И поместить этот список в первое сообщение, пока оно доступно для редактирования. 

 
//whats TD (template define)? because TT is busy
//почемуто этот код в шаблонах на мкл не хочет компилироваться поэтому через дефайн - это Плохо надо бы через шаблоны как то придумать.... привет метаквотам
#define TD1 int
#define TD2 double 
#define EMPY -1 
#define GET this.operator>> 
#define SET this.operator<< 
class CCoordD; 
class CSizeD;
class CCoordBaseD //полностью внутрений класс
   {
   private:
   #define ME CCoordBaseD 
   TEMPL1(T)
   bool Chek(T *a)                  {return CheckPointer(a)!=POINTER_INVALID;}
   TEMPL1(T)
   bool Chek(T a)                   {return a!=(T)EMPY;}
   TD1 Error()                      {Print(__FUNCTION__," ",__LINE__," POINTER_INVALID size"); int a[]; a[0]=0; return (TD1)EMPY;};//wtf??? =P CRASH Error
   TD1 GetA()                       {return c.GetA()+ar;}
   TD1 GetP()                       {return c.Result() + size.GetP()*(TD1)pr;}
   public:
   ME()                                   {Init();} 
   ME(TD1 a)                              {Init(a);} 
   ME(TD1 a,CCoordD &b)                   {Init(a,b);} 
   ME(TD1 a,CCoordD &b,CSizeD &x)         {Init(a,b,x);} 
   ME(TD2 a,CSizeD &b)                    {Init(a,b);} 
   ME(TD2 a,CCoordD &b,CSizeD &x)         {Init(a,b,x);} 
   CCoordD *c;//one coord
   CSizeD *size;//size 
   TD1 ar;
   TD2 pr;//percent проценты
   void Init()                            {ar=(TD1)EMPY; pr=(TD2)EMPY; }  
   TD1 Result()                           {return Chek(ar)?Chek(c)?GetA():ar:Chek(pr)?Chek(size)?GetP():Error():(TD1)EMPY;}
   ME *GetMe()                            {return &this;}
   ME *GetCoorBase()                      {return c;}
   ME *GetSizeBase()                      {return size;} 
   CCoordD *GetCoor()                     {return c;}
   CSizeD *GetSize()                      {return size;} 
   void Init(TD1 a)                       {Init(); SET(a);}
   void Init(TD1 a,CCoordD &b)            {Init(); SET(a); SET(b);}
   void Init(TD1 a,CCoordD &b,CSizeD &x)  {Init(); SET(a); SET(b); SET(x);}
 //  void Init(TD2 p)                     {Init(); pr=p_;}
   void Init(TD2 a,CSizeD &b)             {Init(); SET(a); SET(b);}
   void Init(TD2 a,CCoordD &b,CSizeD &x)  {Init(); SET(a); SET(b); SET(x);}
   void operator >> (TD1 &a)              {a=ar;} 
   void operator >> (TD2 &a)              {a=pr;}  
   void operator >> (CCoordD &a)          {a=GetPointer(c);}  
   void operator >> (CSizeD &s)           {s=GetPointer(size);}  
   void operator << (TD1 &a)              {ar=a;} 
   void operator << (TD2 &a)              {pr=a;}  
   void operator << (CCoordD &a)          {c=GetPointer(a);}  
   void operator << (CSizeD &s)           {size=GetPointer(s);}  
   void operator << (ME &a)               {a>>c; a>>ar; a>>pr; a>>size;}  
   void operator = (CCoordD &a)           {SET(a);}
   void operator = (CSizeD &a)            {SET(a);}
   void operator = (ME &a)                {SET(a);} 
   #undef ME
   #undef TD1
   #undef TD2
   #undef GET 
   #undef SET
   };
   
class CSizeD : public CCoordBaseD
   {
   public:
   CSizeD(){};
   };
   
class CCoordD : public CCoordBaseD
   {
   public:
   CCoordD(){};
   };

class CTX {public:CTX(){}}; 
class CTY {public:CTY(){}};
class CTZ {public:CTZ(){}};
TEMPL(T)
class CCoordA : public T
   {
   public:
   CCoordA() {};
   CSizeD size;
   CCoordD ar; 
   void operator <<(CSizeD &a)   {return ;}
   void operator <<(CCoordD &a)  {return ;}
   };
   
class CCoord
   {  
   public: 
   CCoordA<CTX> X;
   CCoordA<CTY> Y; 
   CCoord ()                              {} 
   bool MouseOn(CMouse &mouse)//px
      {
      //return X.ar.Result()<=mouse.X && X.ar.Result()+X.size.Result()>=mouse.X && GetY()<=mouse.Y && GetY()+GetH()>=mouse.Y;
      return false;
      }
   };  
 

Вобщем либо я что-то не так делаю либо шаблоны на объявление классов (пустых) не хочет работать. Что делает код не особо удобным

Думаю как изменить

 
Такой красивый код разве что на выствку везти. Для чего он, как и что решает неизвестно, но очень красивый...
 
Ребята, раз вы меня учили, дайте и я вас поучу.

Вы должны понимать принципы работы механизмов GUI в первую очередь, а потом начинать писать коды. Должны знать устройство и поведение элементов, их реакции в различных ситуациях. Сначала, представить их как шаблоны, а после создавать экземпляры на подготовленной технической базе, включающей событийную модель, обработчики состояний, явления, координат, привязок и рисования. В конце, у вас получится сырая графическая библиотека на канвасе. До языка разметки будет еще очень далеко. Не говоря уже о редакторе. Но, дерзайте.

Если считаете, что просто возьмете что то готовое и поднимите на уровень выше, значит вы никогда ничего серьезного не разрабатывали. 
 
Реter Konow:
Ребята, раз вы меня учили, дайте и я вас поучу.

Вы должны понимать принципы работы механизмов GUI в первую очередь, а потом начинать писать коды. Должны знать устройство и поведение элементов, их реакции в различных ситуациях. Сначала, представить их как шаблоны, а после создавать экземпляры на подготовленной технической базе, включающей событийную модель, обработчики состояний, явления, координат, привязок и рисования. В конце, у вас получится сырая графическая библиотека на канвасе. До языка разметки будет еще очень далеко. Не говоря уже о редакторе. Но, дерзайте.

Если считаете, что просто возьмете что то готовое и поднимите на уровень выше, значит вы никогда ничего серьезного не разрабатывали. 

Погоди судить - это даже не более чем основа основ. Да и то что я доделаю ГУИ мало вероятно - эт я еще в начале говорил. По поводу больших проектах - скажу так в Вашем коде строчек маловато чтобы тягаться с большими проектами.....


сейчас вопрос почему не работает такой фокус

class CB; 
class CC;

class CBx{public: CBx(){};};
class CBy{public: CBy(){};};
TEMPL(T) 
class CA : public T
   {
   public:
   CA(){}
   CB<T> *b;
   CC<T> *c;
   };
    
TEMPL(T) 
class CB : public CA<T>
   {
   public:
   CB(){}
   };
    
TEMPL(T) 
class CC : public CA<T>
   {
   public:
   CC(){}
   }; 

CB<CBy> cc;
 
Alexandr Andreev:

...

сейчас вопрос почему не работает такой фокус

Кто ж его знает, почему не работает...

Схему библиотеки сначала нужно составить, а потом коды писать. Обычно так делают.
Причина обращения: