Главная страница
    Top.Mail.Ru    Яндекс.Метрика
Форум: "KOL";
Текущий архив: 2007.08.12;
Скачать: [xml.tar.bz2];

Вниз

Вызов CHM справки из MessageBox   Найти похожие ветки 

 
[e]Bu$ter ©   (2006-12-18 00:40) [0]

По порядку:
В разработанной программе такая идея: если пользователь запускает её без параметров, то я она показывают ему MessageBox с флагами MB_ICONINFORMATION or MB_HELP.
Как и положено, при таком вызове функции, появлятеся диалог с кнопками [OK] и [HELP]. По [OK] диалог закрывается, а по [HELP] должен открываться раздел "Синтаксис командной строки" чтоб пользовательно понял как правильно нужно запускать программу. Когда же он наконец её запустит, то по F1 ему нужно показывать уже другой раздел справки - как пользоваться программой.

Вторая задачи, благодаря функции AssignHtmlHelp работает отлично, а вот первая нет - не знаю как заставить MessageBox открывать определённый топик в справке (и как вообще открывать через него справку).
Если сейчас нажимать в нем кнопку [help] то винда говорит, мол

> program.exe - обнаружена обшибка. Проложение будет закрыты.
> Приносим извинения за неудобство.
> ...


Вопросы:
№1: Кто виноват?
№2: Что делать?

Заране благодарю за помощь.

P.S.
WindowsXP2+
Delphi 7
KOL 2.39.1


 
Vladimir Kladov   (2006-12-18 04:50) [1]

Как ваш код вызывает Applet.CallHelp ?


 
[e]Bu$ter ©   (2006-12-18 10:17) [2]

Нет, он ничего не вызывает.
Когда F1 жмёшь, оно "само" открывается, я ничего не делаю :)


 
Vladimir Kladov   (2006-12-18 16:26) [3]

ну так вызовите


 
[e]Bu$ter ©   (2006-12-18 18:14) [4]

Как я по вашему могу это сделать? Т.е. где можно вызвать CallHelp?
У MessageBox ведь нет вроде "mtHelp" в списке возвращаемых значений, как узнать, что пользователь нажал именно эту кнопку (help)? И почему сейчас, когда её жмёшь, выполняется недопустимая операция?
Вот в чём восрос!


 
Vladimir Kladov   (2006-12-18 20:36) [5]

MB_HELP Windows 95/98, Windows NT 4.0 and later: Adds a Help button to the message box. When the user clicks the Help button or presses F1, the system sends a WM_HELP message to the owner.

Выделенное понятно?


 
[e]Bu$ter ©   (2006-12-18 23:19) [6]

Понятно! Большое спасибо.

Проверил в KOLForm1Message

if msg.message = WM_HELP
 then beep(1000, 200);

WM_HELP туда приходит - всё пищит. Но сразу после этого (т.е. в тот момент, когда должна открываться справка), программа выполняет "недопустимую операцию" :(

Понятное дело, что даже если вызывать её из события вручную, то всё-равно, после её открытия - "недопустипая операция".


 
[e]Bu$ter ©   (2006-12-18 23:28) [7]

Я почему такой упрямый: если за работу с CHM справкой, в данном случае, отвечает KOL, то может быть и ошибка эта идёт от туда? Или KOL тут непричём?


 
Vladimir Kladov   (2006-12-19 18:17) [8]

Есть такая фишка, как Search|Find error. Или на худой конец Tools | Debugger options | Language Exceptions | Stop on Delphi Exceptions (включить). И понять, что за AV, и почему оно.


 
[e]Bu$ter ©   (2006-12-20 00:35) [9]

Владимир, не всё так печально! Я знаю про эти фишки, и даже иногда ими пользуюсь (та которая "на худой конец", вроде как даже влкючена по дефолту). Но за подсказку спасибо, как-то со своим кодом я и без этого справляюсь обычно.

Вообщем, с их помощью удалось найти где это AV (кстати, как оно расшифровывается?) Но понять "что за оно", а главное "почему оно" у меня не получилось. Хотя, намёк всё же кое-какой есть:

Удалось выяснить, что ошибку вызывает KOL в процедуре CallWinHelp.

После первого входа в неё, ни одно условие не выполнаяется и в самом её конце выполняется
WinHelp( Applet.Handle, PChar( Applet.GetHelpPath ), Cmd, Context );
после чего, появляется сообщение, которе невозможно было заметить при обыкновенном запуске
---------------------------
Windows Help
---------------------------
Cannot find the E:\dev\program\program.hlp file. Do you want to try to find this file yourself?
---------------------------
Да   Нет  
---------------------------

* намёк я вижу в расширении файла, который оно не может найти

Потом, оно заходит в KOLForm1Message смотрит какой я там возвращаю result (ради эксперимента было false) и идёт обратно в CallWinHelp где на строке
Form.OnHelp( CtxCtl, Context, Popup ); и выполняется "недопустимая операция".

Продолжая эксперимент, я убрал свой обработчик KOLForm1Message и запустил отладку ещё раз. В этом случае оно сразу успешно дошло до Form.OnHelp( CtxCtl, Context, Popup ); и вывалилось с той же ошибкой.

В form.OnHelp у меня ничего нет. Попытки добавить что-то ни к чему не привели.

К сожалению, это всё на что я способен в данной ситауции в это время суток. :(

Скажите, есть надежда, что мы разберёмся чего там происходит?


 
Vladimir Kladov   (2006-12-20 20:21) [10]

просто назначьте OnHelp. Насчет того, почему hlp ищется, а не chm: у вас AssignHtmlHelp вызывается? (до MessageBox"а)


 
[e]Bu$ter ©   (2006-12-21 16:21) [11]


VK> просто назначьте OnHelp.


B> В form.OnHelp у меня ничего нет. Попытки добавить что-то
B> ни к чему не привели

Я пробовал. Ничего не происходило. Всё продолжало падать.


VK> у вас AssignHtmlHelp вызывается? (до MessageBox"а)

Это тоже писал, вызывается, и по F1 всё работает как надо! (включая закрытие справки, при выходе из программы).

Однако, случайно вы меня натолкнули на другую мысль! Дома проверю, отпишу...


 
[e]Bu$ter ©   (2006-12-24 15:06) [12]

Жально, но предоположение не оправдалось.

Чего я только не пробовал, но так ничего и не заработало. Но с проблемой разобрался детально.

• При вызове MessageBox"a в параметр hWnd подставлял и applet.Handle и form.Handle - но при нажатии в нём кнопки Справка, всегда появлялся AV. Если сделать hWnd = 0, то ничего не происходит.
• AssignHtmlHelp вызывается до MessageBox"a (до этого он действительно вызвалось позже. Но не смотря на то, что сейчас ошибка просиходит в процедуре CallHtmlHelp, она всё равно происходит сразу после вызова Form.OnHelp (не важно какой за ним идёт следующий оператор).
• При выполнении CallHtmlHelp, условие Assigned( Form.OnHelp ) всегда истинно, независимо от того назначен ли обработчик на это событие. Поэтому событие onHelp всегда вызывается, но в обработчик KOLForm1Help управление не доходит.
____________________________________________________

Обновился до версии KOL 2.49 (для тестирования, использую PAS_VERSION, но в ASM ошибка там же).

В итоге, AV стал вызываться из
function TControl.ParentForm: PControl;
строкой

 repeat
   Result := Result.fParent;
 until (Result = nil) or not Result.fIsControl; <- вот тут


Сам ParentForm вызывается всё из того же
CallHtmlHelp( Context: Integer; CtxCtl: PControl );,
только уже в строке
Form := CtxCtl.ParentForm;
От сюда понятно, что здесь уже совсем не важно назначен ли обрабочик на событие onHelp, т.к. AV появляется задолго до вызова Form.OnHelp, в котором он происходил раньше (в старой версии KOL).

Вообщем, грабли всё ещё на месте, правда немного другие.
Озадачивался ли кто нибудь этой проблемой? Что посоветуете делать?


 
Vladimir Kladov   (2006-12-24 17:31) [13]

Вы отладчиком пользуетесь? В нем есть возможность просматривать значения переменных. Например, @ Self. Если Handle=0, это исключения не даст. А вот если Applet=nil, то запросто.


 
[e]Bu$ter ©   (2006-12-24 19:49) [14]


> Вы отладчиком пользуетесь?

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

Ещё раз код функции в которой происходит AV:
function TControl.ParentForm: PControl;
begin
 Result := @Self; {1}
 if Result.fIsControl then {2}
 repeat
   Result := Result.fParent; {3}
 until (Result = nil) or not Result.fIsControl; {4}
end;

AV выскакивает в [4] и всё останавливается на этой строке.

Смотрю переменные в соответсвующих строках
[1]: Result = $680012FE
[2]: flsControl = inaccessible value
[3]: Result = $680012FE; fParent = inaccessible value
[4]: Result = $680012FE; flsControl = inaccessible value

Поставил "бряк" на эту функцию и запустил программу. Во всех переменных что-то есть. Вот собсвтенно и причина пораждавшая AV.

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

__________________________________________

Запустил программу полностью, подсунув через Menu -> Run -> Parametrs... нужные для успешного запуска опции. Т.е. теперь как бы и Applet и form созданы.

Отрываю тот диалог, который показывается если параметры ком. строки при запуске заданы были не верно, и жму в нём кнопку "Справка".
Получаю AV в функции
function WndProcHelp( Sender: PControl; var Msg: TMsg; var Rslt: Integer ): Boolean;
на строке

...
   begin
     {$IFDEF USE_PROP}
     Ctl := Pointer( GetProp( HI.hItemHandle, ID_SELF ) );
     {$ELSE}
     Ctl := Pointer( GetWindowLong( HI.hItemHandle, GWL_USERDATA ) );
     {$ENDIF}
     while Ctl <> nil do
     begin
       Ctx := Ctl.fHelpContext; {<-- вот тут}
       if Ctx <> 0 then break;
       Ctl := Ctl.Parent;
     end;
   end
....


Стазу смотрю отладчиком
fHelpContext = inaccessible value

Что теперь делать то? Я в отчаяньи...


 
Vladimir Kladov   (2006-12-24 20:27) [15]

в вашем цикле нет проверки, что достигнут nil.
inaccessible для поля или члена бывает, если указатель объекта/структуры указывает в никуда.


 
[e]Bu$ter ©   (2006-12-24 20:52) [16]


> в вашем цикле нет проверки, что достигнут nil.

В каком именно, первом repeat или втором while?  

И позвольте, разьве это мой цикл? :) Это ж всё из kol.pas


 
Vladimir Kladov   (2006-12-25 17:09) [17]

В вашем- потому что вы его здесь привели. Смотрите, уже в этой строчке
if Result.fIsControl then {2}
[2]: flsControl = inaccessible value
Скорее всего @Self - это уже что-то левое. Можно в Watch-окне (ctrl+shift+W) посмотреть значение переменных Applet, Form1 или что у вас там (если MCK, то Form1.Form) и сравнить с @Self.


 
[e]Bu$ter ©   (2006-12-26 21:55) [18]

Сначала немного дополню предыдущие посты, дабы уточнить картину:
MessageBox вызывается сразу за AssignHtmlHelp в самом начале обработчика KOLForm1FormCreate. Но даже если вызывать его когда программа уже полнотью запущена, .... дальше я уже писал в предыдущем посте [14].

Вот содержимое Self взятое на строке {2} (на ней сейчас всё остановлено):
 Result := @Self; {1}
 if Result.fIsControl then {2}
 repeat
   Result := Result.fParent; {3}
 until (Result = nil) or not Result.fIsControl; {4}


после того как я нажал в MB"е кнопку "Справка":

(264638, $14F6D8, $14F070, 16448, (0, 0), 0, 0, 0, 0, 1244428, 1244444, 2, 0, True, 4278190080, True, True, (out of bound) -1, nil, True, $680012FE, True, True, True, 264638, (out of bound) -40, (out of bound) -10, True, False, 1372272, 16448, nil, $FFFFFFFF, $148398, $14DCA0, $40C6C8, $14F070, $14F6D8, $12FEF0, $77D8057F, True, 67109897, -134201207, 1073758344, $40, False, False, False, -1, 1244940, $77D80537, 264638, $408904, $4088F8, $4040, nil, True, True, True, False, True, True, 64, False, 190, True, 2298740740, 2297954368, True, 4210688, [], True, -536854382, True, -1774649326, True, $1451C000, False, $14DCA0, 4245192, nil, nil, nil, nil, nil, nil, False, False, nil, nil, False, False, 0, 0, nil, nil, nil, 0, (0, 0, 0, 0, (0, 0), (0, 0)), 1373736, 1373800, 0, 1245120, True, True, True, False, 5, $7FFDE000, $7C90E64E, $FFFFFFFE, 9, True, $D70012FF, True, True, 1404, 256, $FDE00000, True, -2141935304, $12FFC8, 200, -8295372, -1459617793, $7C816F, (0, 0), False, False, $40A51C00, nil, False, True, $1000000, $C4000024, $20000000, $14000000, $6000000, False, $340000, $10000, nil, nil, $20000, nil, (nil, $2100000, 0, 412, 0, 0, 0, 18779, 11609, 940, 0, 50, 0, 992, 0, 718, 0, 0, 0, 228, 2, 33538, 1712, 0, 70, 0, 1784, 0, 742, 0, 0, 0, 54738, 53644, 2528, 0, 0, 70, 0, 0, 2600, 0, 742, 0, 0, 0), $D10, $D58, $10, $D4, $1, (276, 3960, 1, 2, 4236, (796, 1)), $13A8, $2, $23F8, 124, 2, 1682469715, 44, 1, $1, 1, 5, 132, 1, [lvoButton,lvoNoSortHeader,lvoMultiselect..lvoGridLines], (out of bound) 44, $56000000, 0, 0, nil, nil, 0, 0, nil, caNone, False, $2000, False, True, (1140850688, 1543518720), (1224759040, 1476414976), (1543524352, 1761629952), (1392537088, 1929410560), 23552, 0, 0, $FC000000, $9C000000, $5B000000, (2553108809, 838860802, 3422552064, -838860798, 33554434, 3825205248, 2, 2, ("ѓ", "њ", #5, #0, #0, "F", #0, #0, #0, "д", #5, #0, #0, "ж", #2, #0, #0, #3, #0, #0, #0, "Т", "Х", "Њ", "С", "М", #8, #0, #0, "F", #0, #0), 5120, 9, -6656, 67108866, 771751936, 4242041517, 11, 17920, 0, 0, 0, 68), 12, $5000003, 167

Как я понимаю, это всякие свойства формы. Т.е. Self как будто-бы куда-то правильно указывает...

Но в строке {1}, да и в {2} тоже, result всё ещё "равен" inaccessible value. После выполнения строки {3}, везде появляются какие-то значения, но видимо - "левые". Отсюда и AV.

Как-то это всё побороть?


 
Vladimir Kladov   (2006-12-27 18:01) [19]

я что-то сильно сомневаюсь, что в свойствах формы будет (out of bound) или строки вроде этой: ("&#402;", "&#339;", #5, #0, #0, "F",
Я же сказал, как проверить: сравнить @ Self как указатель с указателем формы, апплета, что там еще есть.


 
[e]Bu$ter ©   (2006-12-28 00:22) [20]

Владимир, извините, очень не хочется вынуждать вас опускаться до моего уровня и разьяснять "на пальцах", что и как нужно делать (я так понимаю, сейчас мы занимается удалённой пооошааагооовооой отладкой) в этой ситуации, но я к сожалению не совсем понимаю, что значит

> сравнить @ Self как указатель с указателем формы, апплета,
> что там еще есть.

Где его взять, этот "указатель формы"? И что значит "@self как узазатель"? И почему выпишете "@" и "Self" через пробел? Вообщем, вопросов много...

Сейчас однозначно ясно, что до выполнения строки (первый раз)
Result := Result.fParent;
у Result, все свойства (поля, члены?) содержат вразумительные значения. Но на очеденой (в нашем случае - всегда самой первой) итерации, Result начинает указывать вникуда, и естественно, следующая строка
until (Result = nil) or not Result.fIsControl;
порождает AV.

Вам, как отцу KOL (и не только :)), зная механизмы работы библиотеки гораздо проще понять почему (из-за чего) это просиходит. Прошу у вас помощи. Новогодний релиз прогорит по ходу...


 
[e]Bu$ter ©   (2007-01-01 13:48) [21]

1) Как я только в Watch List не добавлял этот @Selft, но значение у него появилось там только один раз. Я правда так и не понял как это получилось, но тогда оно точно не совпадало со значением (адресом) form1.form. Подозрительно то, что оба они имели какие-то старнные по виду значения первое EEEEFEFE, а другое FEEEEEFE (данные приблизительные).
Во всех остальных попытках @Self "был равен" Variable "Self" inaccessible here due to optimization.

2) Зная, что сообщение WM_HELP "perent"у" посылается когда ещё форма до конца не создана (в самом начале KOLForm1FormCreate), возникает вопрос: а возможно ли тут в принципе реализовать так задуманное? Что считается parent"ом когда формы ещё нет?


 
Vladimir Kladov   (2007-01-01 14:56) [22]

Так о том и речь. Чтобы форсировать создание дескриптора окна, надо не просто к Handle обратиться, но вызвать GetWindowHandle. А если Applet"у ничего не присвоено, то чего вы хотите от него вообще.



Страницы: 1 вся ветка

Форум: "KOL";
Текущий архив: 2007.08.12;
Скачать: [xml.tar.bz2];

Наверх




Память: 0.53 MB
Время: 0.042 c
2-1184582897
Kostafey
2007-07-16 14:48
2007.08.12
Получить список таблиц из Access-файла.


2-1184152074
Vasyl
2007-07-11 15:07
2007.08.12
Поиск


2-1184731192
Jann
2007-07-18 07:59
2007.08.12
работа с файлом dbf


2-1184515931
Zagaevskiy
2007-07-15 20:12
2007.08.12
Язык системы


2-1184332482
GMH
2007-07-13 17:14
2007.08.12
вызываемая Getmodulefilemameex





Afrikaans Albanian Arabic Armenian Azerbaijani Basque Belarusian Bulgarian Catalan Chinese (Simplified) Chinese (Traditional) Croatian Czech Danish Dutch English Estonian Filipino Finnish French
Galician Georgian German Greek Haitian Creole Hebrew Hindi Hungarian Icelandic Indonesian Irish Italian Japanese Korean Latvian Lithuanian Macedonian Malay Maltese Norwegian
Persian Polish Portuguese Romanian Russian Serbian Slovak Slovenian Spanish Swahili Swedish Thai Turkish Ukrainian Urdu Vietnamese Welsh Yiddish Bengali Bosnian
Cebuano Esperanto Gujarati Hausa Hmong Igbo Javanese Kannada Khmer Lao Latin Maori Marathi Mongolian Nepali Punjabi Somali Tamil Telugu Yoruba
Zulu
Английский Французский Немецкий Итальянский Португальский Русский Испанский