:: Курилка
DataEnvironment'y посвящается
JS

Сообщений: 12264
Откуда: Эстония
Дата регистрации: 04.09.2000
Первая часть:

www.hot.ee

или для тех, у кого заблокирован www.hot.ee, между прочим сайт эстонской телефонной компании

kodu.neti.ee

Вторая часть:

www.hot.ee

или для тех, у кого заблокирован www.hot.ee, между прочим сайт эстонской телефонной компании

kodu.neti.ee


После всех споров по-поводу DE так и хочется иногда сказать фразу из рекламы:
Как, вы еще не используете DE, тогда мы идем к вам!.
А если серъезно, то я бы не стал ругать этот отнюдь не плохой объект.
Не было бы его, у меня иногда были бы большие выкрутасы.



[i][small][color=Gray]Отредактировано (16.06.04 17:40)


------------------
Knowledge is better than ignorance!
Website: juri.foxhelp.eu
Ratings: 0 negative/0 positive
Re: DataEnvironment'y посвящается
Igor Korolyov

Сообщений: 34580
Дата регистрации: 28.05.2002
Эх, ну не могу удержаться от того чтоб не прокомментировать маленько (с целью возможно кой чего прояснить/развить дискуссию)
I Про "жесткую пропись пути" - не отметил что как правило пути не прописываются в объектах DE полностью - обычно там относительные пути (относительно размещения формы), просто "умный" Property Window "переводит" относительный путь в абсолютный. Но конечно бывают и ситуации когда прописан полный путь (например когда форма и данные размещены на разных дисках). В первом случае ситуация не столь плачевна - если проект переносится/распространяется без изменения иерархии папок то всё нормально - и даже если иерархия папок изменена, но "изначальной" папки нету (или там нету данных) а "новая" папка выбрана как SET DEFAULT или указана в SET PATH то фокс таки найдёт данные (плохо это конечно - мало ли где он ещё может одноименную таблицу найти - но не смертельно). Во втором случае всё гораздо хуже - начиная от обращения чёрт-те куда (к CD-накопителям, или через сеть к машине разработчика .
II Про то "где и когда подменять пути". Нельзя говорить что "не имеем доступа к DE и его методам" - доступ есть, причём именно через переопределение путей в методе DE.BeforeOpenTables работает код предлагаемый самой MS (кстати нехудо было бы и ссылку на это статью KB поместить - всё-же "в тему"). Другой вопрос в том, что это "технологически" невыгодно/неудобно - ибо нехорошо заниматься Copy/Paste в ОО среде Даже если вставлять в этот метод всего 1 строку - вызов соответствующей функции.
Ещё один способ - это "просто убрать AutoOpen" - тогда действительно можно пути поменять в Load и потом явно вызвать OpenTables() но это так-же не слишком красиво по тем-же причинам (можно и забыть эту установку сделать, а субклассировать DE стандартными методами нельзя).
Предложенный же способ меня не устраивает по той простой причине, что у тебя будет происходить "двойная работа" - сначала автооткрытие всех источников, потом закрытие, подмена путей и повторное открытие - это крайне негативно сказывается на прои
зводительности
Возикает извечный вопрос "Что делать" - тут могу предложить лишь один способ (коим и пользуюсь поныне и надеюсь в VFP9 MS ничего не "поломала" и он продолжит мне служить - называется он "субклассирование базового класса" Был открыт когда-то давно уважаемым Michael Drozdov, принят за забавную багофичу и забыт, а я вот "подогрел и обобрал" (с)
Суть махинации проста до безобразия:
1) определяем класс - замену базового класса DE:
DEFINE CLASS DEHook AS DataEnvironment
Name = "DataEnvironment"
* Внимание - эта строка крайне важна, именно задание в качестве
* имени класса названия базового класса, позволяет этому классу
* быть классом-заменой.
PROCEDURE BeforeOpenTables
MESSAGEBOX("Псевдо-базовый код метода")
ENDPROC
ENDDEFINE
2) Создать экземпляр вышеописанного класса:
PUBLIC goDEHook
SET PROCEDURE TO DEHook.prg
m.goDEHook = CREATEOBJECT ("DEHook")
3) Если в методе DE.BeforeOpenTables для некоторой формы есть некоторый
уникальный (для данной формы) код, то надо не забыть вызвать и наш новый
псевдо-базовый код через DODEFAULT().
4) Для снятия хука и восстановления поведения но умолчанию надо убрать
объект goDEHook и прочистить мозги фоксу на предмет кеширования данного
класса:
m.goDEHook = .Null.
RELEASE goDEHook
CLEAR CLASS DataEnvironment
Это решает все проблемы с "технологичностью" - код описан всего в одном месте и нигде ничего уже не "забудешь проставить" Более того - этот код будет обрабатывать DE отчётов! О чём ты забыл упомянуть
III Про то "как хранить пути" - для начала надо определиться с тем, что мы не должны "передавать пути параметрами" и потому нам действительно не принципиально в каком метода будет идти замена. Твоя идея в целом правильна, но вот в деталях...
1) Объект goApp (кстати зачем ты ему поставил префикс локального?) IMHO должен быть гораздо более мощный чем "просто хранилище свойств" и потому не надо стремиться делать его от Empty класса - в Empty классе невозможно определить методы, а значит он нам
не годиться
2) Код "заполнения" IMHO весьма специфичен - я бы вообще не стал никакого кода писать - просто сказал что должны быть такие-то и такие-то структуры (у меня кстати именно коллекция и используется - как "подобъект" goApp-а для VFP7 это "моя коллекция" для VFP8 - уже встроенный класс - я специально сделал их "практически идентичными" по интерфейсам). Как доп. аргументы: разные базы могут лежать не просто в разных подпапках одной папки, а например на разных серверах... Да и не нужно обычно добавлять "всё что ни попадётся" в этот список - т.е. идея с внешней настройкой более интересна - например ini/dbf-файл с набором "путей"+"имён".
3) Для простоты я не загружаю в "коллекции путей" всех возможных вариантов, а только 1 - ибо в один конкретный момент времени у меня программа работает только с одной конкретной базой (не в смысле с одной DBC - их то может быть много разных, а в смысле с "набором баз одного предприятия") И для "замены" надо просто перезаполнить эти коллекции и (возможно, даже желательно, но не обязательно) переоткрыть все формы - чтоб не возникало путаницы.
4) Для DBC и для FreeTable я использую 2 разных коллекции "путей" Индексные ключи коллекций - это соответственно имя DBC и имя Free-таблицы. Заполнение коллекций идёт не напрямую, а через методы goApp - OpenDatabase(tcFullPathName, tnMode) (помимо регистрации в коллекции БД ещё и открывается в нужном режиме), SetFreeTableLocation(tcFullPathName) (таблица конечно не открывается Ну и 2 обратных метода:
CloseDatabase(tcName) и ResetFreeTableLocation(tcName).
IV Про то "как надо заменять пути" - в принципе нормальный подход, пара замеченных тонкостей:
1) DE может и не называться DataEnvironment разработчик может сменить Name (потому надо тогда орг. вопростом это решать).
2) У тебя рассмотрен только вариант "всё в одной папке", а вполе возможно что БД разнесена по разным папкам (особенно если подсистема сложная - у нас даже для Clipper программ были особые папки скажем для НСИ).
Для сравнения приведу и свой код - может какие идеи пригодяться
DEFINE CLASS DEHook AS DataEnvironment
Name = "DataEnvironment"
__cversion = "0.17 от 18/4/2003 IK"
PROCEDURE BeforeOpenTables
IF TYPE ("m.goApp.Name") == "C"
LOCAL loCursor, lcDBC, lnDSID
m.lnDSID = SET("Datasession")
IF m.goApp._DEBeforeOpenTablesHook(This, m.lnDSID)
* Не заблокировали в метода объекта приложения
FOR EACH loCursor IN This.Objects
IF "CURSOR" $ UPPER (m.loCursor.Class)
IF EMPTY (m.loCursor.Database)
* Свободная таблица
IF m.goApp.oFreeTableList.Count > 0 AND ;
m.goApp.oFreeTableList.GetKey (UPPER (JUSTSTEM (m.loCursor.CursorSource))) # 0
m.loCursor.CursorSource = m.goApp.oFreeTableList.Item (UPPER (JUSTSTEM (m.loCursor.CursorSource)))
ELSE
m.loCursor.CursorSource = FULLPATH (JUSTFNAME (m.loCursor.CursorSource))
* Если не зарегистрированна, то будет искаться по SET PATH
ENDIF
ELSE
* Обзор или таблица БД
IF m.goApp.oDBCList.Count > 0 AND ;
m.goApp.oDBCList.GetKey (UPPER (JUSTSTEM (m.loCursor.Database))) # 0
m.loCursor.Database = m.goApp.oDBCList.Item (UPPER (JUSTSTEM (m.loCursor.Database)))
ELSE
m.loCursor.Database = FULLPATH (JUSTFNAME (m.loCursor.Database))
* Если не зарегистрированна, то будет искаться по SET PATH
ENDIF
ENDIF && EMPTY (m.loCursor.Database)
ENDIF && "CURSOR" $ UPPER (m.loCursor.Class)
ENDFOR
ENDIF
ENDIF
ENDPROC
ENDDEFINE
Ну минусы/баги тут видны невооруженным глазом - давненько писал Не рассчитывал на появление классов CURSORadapter...
Зато видим вызов m.goApp._DEBeforeOpenTablesHook - этот метод объекта приложения переключает датасессию (чтоб код мог работать в DS нашей формы) и вызывает абстрактный метод m.goApp.DEBeforeOpenTablesHook() - это хорошее место для размещения всякого установочного кода, который нужен для всех форм/отчётов в приложении - программируется прикладным программистом исходя из его предпочтений - пресловутые SET TALK OFF, SET DELETED ON, SET DATE GERMAN
и всё-всё-всё прочее что "scope to the current datasession" - MS VFPTeam не удосужилось никак этот аспект улучшить (например "наследовать" установки Public или просто текущей DS для всех вновь создаваемых DS) так мы их сбоку обойдём

Да что-то меня сегодня потянуло на демагогию Есть ещё и конструктивная критика по другим статьям (кой чего ну просто просится чтоб "уточнить и расширить") но это в другой раз.




------------------
WBR, Igor
Ratings: 0 negative/0 positive
Re: DataEnvironment'y посвящается
JS

Сообщений: 12264
Откуда: Эстония
Дата регистрации: 04.09.2000
2Игорь! Спасибо за отличный и подробный комментарий, будем потихоньку развивать дискуссию.
А так как сегодня не дадут нормально пообщаться - ревизия архивов - то отвечать и задавать
вопросы буду частями.
Цитата:
I Про "жесткую пропись пути" - не отметил что как правило пути не прописываются в объектах DE полностью - обычно там относительные пути (относительно размещения формы), просто "умный" Property Window "переводит" относительный путь в абсолютный. Но конечно бывают и ситуации когда прописан полный путь (например когда форма и данные размещены на разных дисках). В первом случае ситуация не столь плачевна - если проект переносится/распространяется без изменения иерархии папок то всё нормально - и даже если иерархия папок изменена, но "изначальной" папки нету (или там нету данных) а "новая" папка выбрана как SET DEFAULT или указана в SET PATH то фокс таки найдёт данные (плохо это конечно - мало ли где он ещё может одноименную таблицу найти - но не смертельно). Во втором случае всё гораздо хуже - начиная от обращения чёрт-те куда (к CD-накопителям, или через сеть к машине разработчика
По-поводу относительного пути - мое упущение и об этом стоило написать сразу - это предмет для редактирования статьи (пора уже, наверное, вместе писать) и об этом речь идет в третьей части, и как раз здесь большинство новичков спотыкается - при работе со свойствами DataEnvironment. Я еще не успел отредактировать остальные части - всего 7 (первые три - DataEnvironment, как native form object, последующие три - DataEnvironment, как класс и последняя - тестовое приложение, где есть ссылка на него и описание).

Цитата:
II Про то "где и когда подменять пути". Нельзя говорить что "не имеем доступа к DE и его методам" - доступ есть, причём именно через переопределение путей в методе DE.BeforeOpenTables работает код предлагаемый самой MS (кстати нехудо было бы и ссылку на это статью KB поместить - всё-же "в тему"). Другой вопрос в том, что это "технологически" невыгодно/неудобно - ибо нехорошо заниматься Copy/Paste в ОО среде Даже если вставлять в этот метод всего 1 строку - вызов соответствующей функции.
Игорь! В статье я имею в виду собственный базовый класс формы и классы форм, выстраиваемые на ее основе, что иногда вызывано необходимостью иметь строго "прорисованную" и вылизанную форму, и с которыми работаем в визуальном дизайнере классов. При работе с классом формы мы действительно не имеем возможности работать с DataEnvironment. Здесь может быть несколько неудачно получилось с рисунками - для того, чтобы показать свойства и методы DE пришлось делать это не в дизайнере классов, а в дизайнере форм. (Это тоже может сбивать с толку и надо подумать, как получше отобразить это графически).

А вот когда уже мы работаем с формой, создаваемой на базе класса, в дизайнере форм, то мы уже конечно можем работать с методами событий объекта DataEnvironment, хотя при этом теряются преимущества OOP, то есть должны каждый раз прописывать код в соответствующих методах и как справедливо замечено - что это "технологически" невыгодно/неудобно - ибо нехорошо заниматься Copy/Paste в ОО среде. И это тоже нужно будет подкорректировать в статье.

Что же касается статьи 160916, то она уже переведена и ссылка на нее в третьей части.

Цитата:
Ещё один способ - это "просто убрать AutoOpen" - тогда действительно можно пути поменять в Load и потом явно вызвать OpenTables() но это так-же не слишком красиво по тем-же причинам (можно и забыть эту установку сделать, а субклассировать DE стандартными методами нельзя).
Предложенный же способ меня не устраивает по той простой причине, что у тебя будет происходить "двойная работа" - сначала автооткрытие всех источников, потом закрытие, подмена путей и повторное открытие - это крайне негативно сказывается на производительности

Давай посмотрим на третий абзац второй части:

Цитата:
Дело в том, что свойство AutoOpenTables объекта DE можно использовать как флаг, в зависимости от значения которого мы либо будем перестраивать окружение, либо нет. С одной строны, это для особо ленивых, так как все можно сделать гораздо более элегантнее. С другой стороны - это удобно, так как установка значения этого свойства в False (.F.) заставит форму посмотреть - а с этим-ли окружением мне нужно работать?
То есть, в простейшим случае код в методе, ассоциированном с событием Load класса формы можно видоизменить следующим образом:


If !This.DataEnvironment.AutoOpenTables
If !This.udf_SetDE("DE1")
=MESSAGEBOX(;
"Something is going wrong in Danish Kingdom!"+chr(13)+;
"Where is this ragged programmer Shutenko?",;
16,;
"Error occurs in application";
)
Return .F.
Endif
Endif

Справедливо и не используется мною в реальных проектах. То есть когда разрабатывается форма на основе подобного класса в дизайнере форм, то свойство AutoOpenTables всегда устанавливается в .F. Это вроде бы видно из примера кода, однако можно подчеркнуть особо. В класс формы можно ввести свойство типа fvl_UseAutoOpenTables (по умолчанию устанавливается в False) и ввести его проверку в методе события OpenTables, но опять-таки надо прописать код и хотя он короче, но он все-таки есть, например:
IF !This.Parent.fvl_UseAutoOpenTables
NODEFAULT
ELSE
DODEFAULT()
ENDIF
и затем в функции подмены путей выполнить:
This.fvl_UseAutoOpenTables=.T.

Поскольку еще в первой части я оговорил, что данное применимо к структуре концерна или необходимостью работы с одинаковыми базами, то нужно некоторое пояснение.
Имеются реальные приложения, первое было сделано на VFP 6.0 для своего приятеля - присяжного адвоката (опять-таки бесплатно - программист и бизнесмен в одном стакане вещь трудно совместимая, особенно когда речь идет о друзъях), который ведет дела нескольких фирм (присяжные адвокаты занимаются не только судебными делами, но и разными международными договорами, декларированием и массой других разных дел и в общем-то объемы данных весьма приличные). И иногда ему нужны тождественные документы. Все было сделано на описанном принципе, когда он просто в форме через combobox выбирает другую фирму, просматривает или копирует какие-то уже готовые решения (поэтому и используются вылизанные до "абсурда" классы).
И в статье приведено, конечно же, упрощенное:
If !This.udf_SetDE("DE1")
Реально же, в вызове функции передается параметр, связанный с последним окружением, в котором он работал последним до выхода из программы. А вот сообщение в Messagebox - именно такое, каким он его один раз за историю программы увидел.
Это его любимая фраза - неладно что-то в Датском королевстве.

Идем далее

От:

Цитата:
Возикает извечный вопрос "Что делать"
и до:

Цитата:
Это решает все проблемы с "технологичностью" - код описан всего в одном месте..."

Абсолютно справедливо. Уже сам по себе направшивается вопрос - может быть добавить вводную статью и для начала описать все возможности создания DE от программного до класса (VFP8) и последующей работы с ним? поскольку приведенные статьи рассматривают частный пример использования...

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

Цитата:
1) Объект goApp (кстати зачем ты ему поставил префикс локального?)
IMHO должен быть гораздо более мощный чем "просто хранилище свойств" и потому не надо стремиться делать его от Empty класса - в Empty классе невозможно определить методы, а значит он нам
не годиться

Согласен, здесь немного некорректное использование префикса, так как не хотел чего-то придумывать и в данном случае они означают localization object, сюда заносятся то что уже показано и установки из ini-файла и из регистра. В первых строках идет вызов процедуры декларирования динамических библиотек, размещенной здесь же.
Поскольку здесь только фрагмент, то не стал править, а вообщем-то учту.
Что же касается использования Empty класса, то меня в данном случае он как раз устраивает, так как хранит только установки, которые доступны повсюду в приложении. Для обслуживания приложения создается объект диспетчера (я это так называю, может быть неудачно, но тут уж сила привычки), который на базе установок определяет наличие обновления, осуществляет кое-какие проверки, что-то грузит дополнительно и так далее. Вот он называется dspApplication и тождественнен по смыслу, но не функциональности goApp, как это использовалось начиная с третьей версии.

Цитата:
2) Код "заполнения" IMHO весьма специфичен - я бы вообще не стал никакого кода писать - просто сказал что должны быть такие-то и такие-то структуры (у меня кстати именно коллекция и используется - как "подобъект" goApp-а для VFP7 это "моя коллекция" для VFP8 - уже встроенный класс - я специально сделал их "практически идентичными" по интерфейсам). Как доп. аргументы: разные базы могут лежать не просто в разных подпапках одной папки, а например на разных серверах... Да и не нужно обычно добавлять "всё что ни попадётся" в этот список - т.е. идея с внешней настройкой более интересна - например ini/dbf-файл с набором "путей"+"имён".

Для примера хоть что-то показать надо.



[i][small][color=Gray]Отредактировано (17.06.04 16:31)


------------------
Knowledge is better than ignorance!
Website: juri.foxhelp.eu
Ratings: 0 negative/0 positive
Re: DataEnvironment'y посвящается
Igor Korolyov

Сообщений: 34580
Дата регистрации: 28.05.2002
Сразу скажу что когда писал, только первую часть просмотрел потому и
часть непоняток возникла.
Цитата:
В статье я имею в виду собственный базовый класс формы и
классы форм
Тогда это надо подчеркнуть - что это именно классы форм,
а не scx-формы, а то возникает законный вопрос - вот я смотрю на DE формы, а
мне говорят что его нету
Кстати я пока что не вижу реальных преимуществ "отвязанного DE - класса".
Т.е. не сталкивался с такими ситуациями, когда много форм используют
идентичные DE - обычно всегда возникают какие-то вариации, и реально каждая
форма имеет свой уникальный набор курсоров/связей в DE. А значит в плане
субклассирования достаточно иметь просто 1 _base класс DE (пустой) и массу
"конечных" DE-классов/объектов т.е. то как оно изначально было задумано
MS-ом... Реально субклассированием непустого DE я так и не занялся...
Да и тут скорее нужно не субклассирование, а "агрегирование" - т.е. из 2-х
имеющихся DE слепить один новый - да так чтобы ничего не пересекалось и не
взаимодействовало "неясным образом". Вот тут пока самое слабое место что я
вижу в DE... Как можно привязать DE к некоторому контейнеру, как можно
организовать взаимодействие нескольких DE в одной форме и одной датасессии
соответственно... Пока только вопросы без ответов.
Цитата:
В класс формы можно ввести свойство типа fvl_UseAutoOpenTables (по
умолчанию устанавливается в False) и ввести его проверку в методе события
OpenTables
А оно к тому моменту уже доступно? В режиме AutoOpen
когда порядок срабатывания событий "особый" (некоторые даже говорять что это
ужасно криво и неправильно - типа до Init ничего срабатывать не должно)
Цитата:
И иногда ему нужны тождественные документы. Все было сделано на
описанном принципе, когда он просто в форме через combobox выбирает другую
фирму, просматривает или копирует какие-то уже готовые решения
А, ну
тогда понятно... Хотя тут можно сделать разделение по иному принципу -
завести общую базу "шаблонов", и копировать исключиетльно из неё, а не "от
чужой фирмы"... И кстати структура "общей базы" где разделение сделано
только по полю "код предприятия/клиента" тоже может быть применено. Но это
так - к слову.
Цитата:
Абсолютно справедливо, но к сожалению применимо только в невизуальном
программном описании
Так только один этот класс-хук описан
невизуально Все формы то визуальные! его прелесть как раз в том, что не
приходится отказываться от визуальных дизайнеров, как порой требуется в
случае с "внедрением своего класса DE" - особливо в VFP6SP5... Он вообще
работает "из-под" т.е. прозрачно для всего остального - они и не подозревают
что вместо "фоксового базового класса DE" используется моя прослойка. За
единственным исключением - переопределением методов - тогда надо "вспомнить"
что есть ещё и мой код и вставить DODEFAULT()
Цитата:
для начала описать все возможности создания DE
IMHO сильно
обширно получится и будет только путать новичка... Просто скажи что это один
из возможных путей,а про другие только упомяни (перечисли) если уж так
решил.
Цитата:
А что касается стандартных фоксовский отчетов, то я использую их
редко. В основном перегонка в подготовленные шаблоны Excel или Word.
У меня тоже




------------------
WBR, Igor
Ratings: 0 negative/0 positive
Re: DataEnvironment'y посвящается
JS

Сообщений: 12264
Откуда: Эстония
Дата регистрации: 04.09.2000
Цитата:
А оно к тому моменту уже доступно? В режиме AutoOpen
когда порядок срабатывания событий "особый" (некоторые даже говорять что это
ужасно криво и неправильно - типа до Init ничего срабатывать не должно)

В том и анекдот, что уже доступно, хотя форма вроде как бы и не загружена.

Цитата:
Так только один этот класс-хук описан невизуально
Игорь, пока ты, видимо, еще читал, я уже поправил. Какая-то отвязка происходит
когда видишь define class - сразу переключаешься на процедурное... Извини!

Цитата:
Хотя тут можно сделать разделение по иному принципу -
завести общую базу "шаблонов", и копировать исключительно из неё, а не "от
чужой фирмы"...
Шаблоны здесь не совсем подходят, хотя и используются. Копируются какие-то фрагменты ранее удачно составленного текста, или признаковая группа (это он так называет - "в соответствии со статьей nn § nn закона" и т.п.
Я уж ему и словарь фраз сделал, говорит, что так привычнее, сразу видит проблему,
но это уже так - отвлеклись.

Цитата:
Кстати я пока что не вижу реальных преимуществ "отвязанного DE - класса".

Я думаю, что здесь есть определенная связь между введенными в 8-й версии классами DE и CursorAdapter, и это предположение основано на том, что построитель DE "заточен" под работу с последним. Даже если мы создадим класс обычного курсора и потом попробуем добавить его в DE с помощью построителя, мы получим ошибку - <имя_курсора> is no CursorAdapter subclass.
Но опять-таки - это только предположение.
Хотя без всяких проблем мы можем вставить тот же заготовленный класс обычного курсора в класс DE в дизайнере классов без всяких проблем.

И вообще в документации есть несколько противоречий. Но об этом позже.



[i][small][color=Gray]Отредактировано (18.06.04 12:34)


------------------
Knowledge is better than ignorance!
Website: juri.foxhelp.eu
Ratings: 0 negative/0 positive
Re: DataEnvironment'y посвящается
Sergey Titow
Автор

Сообщений: 2242
Дата регистрации: 12.09.2000
Цитата:
В режиме AutoOpen когда порядок срабатывания событий "особый" (некоторые даже говорять что это ужасно криво и неправильно - типа до Init ничего срабатывать не должно)
Это не некоторые - это сам прародитель этой объектной схемы.
И не в "режиме AutoOpen", а при AutoOpen=.t. в случае scx формы.
И не просто "до Init" самого объекта - а даже до Load его родителя

PS. Я уже говорил, что это надо было только для заточки под визуальную среду разработки. В ран-тайме это вообще ни для чего не надо.
И "ужасную кривость" вижу не в том, что это сделано именно так, а в том, что именно так M$ поступает всегда, когда "спирт мешает спорту".
И до сих пор не понимаю, почему ДЕ нет в качестве стандартного члена класса формы...
PPS. Искать способ применения багофич - занятие на любителя. Для меня лично - удовольствие ниже среднего.



[i][small][color=Gray]Отредактировано (20.06.04 18:40)


------------------
Ratings: 0 negative/0 positive


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

On-line: 71 (Гостей: 71)

© 2000-2024 Fox Club 
Яндекс.Метрика