Re[2]: Я в шоке GetMessage()
От: Andrew S Россия http://alchemy-lab.com
Дата: 12.09.05 15:36
Оценка: 14 (1) +1
К>Правда в документации. (А сила, брат, она в ньютонах).
К>GetMessage

К>GetMessage ждёт появления виндовских сообщений в очереди сообщений текущего потока, и когда дожидается — извлекает очередное сообщение и возвращает false (если это сообщение было WM_QUIT) либо true (во всех остальных случаях).


Нет, не совсем так. Это распространенное заблуждение, но GetMessage не возвращается при приходе очередного сообщения. У потока как минимум 3 интересующих нас очереди сообщений: очередь сообщений, помещенных туда при помощи Send, ..., при помощи Post и очередь input сообщений. По крайней мере, так выглядит это извне. Так вот, GetMessage не возвращается на сообщения, посланные при помощи Send (на установленный флаг QS_SENDMESSAGE), и это явно сказано даже в документации:

function dispatches incoming sent messages until a posted message is available for retrieval


У Рихтера шаги работы GetMessage приведены как:

1. If the QS_SENDMESSAGE flag is turned on, the system sends the message to the proper window procedure. Both the GetMessage and PeekMessage functions handle this processing internally and do not return to the thread after the window procedure has processed the message; instead, these functions sit and wait for another message to process;
2. If messages are in the thread's posted-message queue, GetMessage and PeekMessage fill the MSG structure passed to these functions, and then the functions return. The thread's message loop usually calls DispatchMessage at this point to have the message processed by the appropriate window procedure.
3. If the QS_QUIT flag is turned on, GetMessage and PeekMessage return a WM_QUIT message (where the wParam parameter is the specified exit code) and reset the QS_QUIT flag.
4. If messages are in the thread's virtualized input queue, GetMessage and PeekMessage return the hardware input message.
5. If the QS_PAINT flag is turned on, GetMessage and PeekMessage return a WM_PAINT message for the proper window.
6. If the QS_TIMER flag is turned on, GetMessage and PeekMessage return a WM_TIMER message.


К>Причём программа не циклится в недрах системы, а висит на ожидании. Т.е. прервать (break) этот поток отладчиком не получится.


К>Если хочешь проверить, не ожидая — пожалуйста: PeekMessage.

Ровно такой же алгоритм, за исключением того, что эта функция не ожидает прихода posted сообщений, а просто возвращает FALSE, если их нет.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[10]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 08:48
Оценка: 3 (1) +1
Здравствуйте, Votblin, Вы писали:

V>Спасибо за ответ. Но чтот я и та ки сяк пытался поюзать этот хук. Ничего не выходит.


V>МОжет подскажете все таки?


посмотрел я посты — действительно, хук + сабклассинг более верно.
делается это примерно так.

нам потребуется dll c двумя процедурами. одна из них будет хук-процедурой, вторая — новой оконной процедурой.
то есть интерфейс такой


// hookDll.h

// экспортируется из длл
void DLL_EXPORT SetHook( HMODULE currentModule );
void DLL_EXPORT ClearHook( HMODULE currentModule );
LRESULT CALLBACK DLL_EXPORT CBTProc(int nCode, WPARAM wParam, LPARAM lParam);


про тело можно позже поговорить.
можно поставить так ( это уже исходник приложения, то есть exe-шника)

// appUsingHook.cpp

typedef void ( *STARTHOOKPROC )();

void ApplicationSetHook() {
    HMODULE dll = LoadLibrary("hookDll.dll");
    if ( dll != INVALID_HANDLE_VALUE ) {
        STARTHOOKPROC proc = (STARTHOOKPROC) GetProcAddress( dll, "SetHook" );
        if ( proc != NULL ) {
            proc( dll );
        }
        FreeLibrary( dll );
    }
}    

void ApplicationClearHook() {
    HMODULE dll = LoadLibrary("hookDll.dll");
    if ( dll != INVALID_HANDLE_VALUE ) {
        STARTHOOKPROC proc = (STARTHOOKPROC) GetProcAddress( dll, "ClearHook" );
        if ( proc != NULL ) {
            proc( dll );
        }
        FreeLibrary( dll );
    }
}


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

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


//hookDll.cpp
HHOOK hook;

WNDPROC oldProc = NULL;
void SubclassWindow( HWND hwnd );
LRESULT CALLBACK NewWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);


void DLL_EXPORT SetHook( HMODULE currentModule ) {
    hook = SetWindowsHookEx( WH_CBT, CBTProc, currentModule, 0 );
}

void DLL_EXPORT ClearHook() {
    UnhookWindowsHookEx( hook );
}

LRESULT CALLBACK DLL_EXPORT CBTProc(int nCode, WPARAM wParam, LPARAM lParam) {
    if ( nCode < 0 )
        return CallNextHookEx( hook, nCode, wParam, lParam );
    
    switch ( nCode ) {
        case HCBT_CREATEWND: {
            if ( lp->lpszClass != 0 && stricmp(lp->lpszClass, "WindowClassName") == 0 ) {
                SubсlassWindow( (HWND) wParam );
            }
            break; }
    }
    return CallNextHookEx( hook, nCode, wParam, lParam ); }
}

void SubclassWindow( HWND hwnd ) {
    if ( oldProc == NULL ) {
        oldProc = SetClassLongPtr( hwnd, GCLP_WNDPROC, NewWndProc );
    }
}

LRESULT CALLBACK NewWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam) {
    switch ( msg ) {
        case WM_KEYDOWN {
            ::MessageBox( hwnd, "You pressed key", "KEY", MB_OK );
        }
    }
    return oldProc( hwnd, msg, wParam, lParam );
}


момент — CallNextHookEx() получает хендл хука, который был установлен. а если я устанавливаю его в одном процессе, например, в своем, а он потом вызывается другой, например из калькулятора:
1) в адресное пространство калькулятора загружается hookDll.dll
2) там ищется функция CBTProc
3) вызывается оная.

и внутри неё нам нужно вызвать следующий хук ( они там в очереди все стоят ). но SetWindowsHookEx я вызывал в другом процессе, значит и хендл хука в другом процессе. вот тут-то и пригодятся shared memory section. они позволяют сказать линкеру, что вот эта область память будет доступна для всех длл, неважно где и когда они загрузились.
конкретно, в эту область нам надо поместить HHOOK hook. в результате получается


//hookDll.cpp
#pragma data_seg( .shared ) 
HHOOK hook = NULL;
#pragma data_seg() 
#pragma comment(linker, /section:.shared,RWS )

WNDPROC oldProc = NULL;
void SubclassWindow( HWND hwnd );
LRESULT CALLBACK NewWndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam);



зы.. все это, неоднократно обсуждалось на форуме
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[10]: Я в шоке GetMessage()
От: Andrew S Россия http://alchemy-lab.com
Дата: 13.09.05 06:11
Оценка: +1 :)
V>Относительно статьи. Я, конечно, может и ошибаюсь, но она меня не совсем устраивает. Я писал конечно длл компоненты для 1с на си шарпе, но на другой фирме. А здесь это сделать нелегко. У нас около 30 филиалов разбросаных по Украине. и устанавливать на кждом по .NET Framework не сахар . Кроме того, есть калькуляторы, у которых установлено Вынь 98. А всего этих компьютеров насчитывается около 150 штук!

Нда, что делает с человеком занятие 1с. При чем тут Net? Там был показан способ создания Com сервера для 1c. С тем же успехом это можно сделать и на ATL.

V>Неужто придется выбирать вариант "удалять гланды через анус"?


V>Вот еще одна статья: http://www.codeguru.com/Cpp/W-P/system/keyboard/article.php/c5699/ . Вот только мне не виртся, что получив HANDLE окна я не могу достучаться до WM_CHAR этого окна и получить код символа. В вышописанной статье путь конечно супер гиморный. Может посоветуете билиотеки какие?


Все, что надо делать, я уже написал. Внимательно прочитайте написаное, ипользуйте поиск по форуму. Тема сабклассинга окна в чужом приложении тут обсуждалась, и даже были примеры кода. Но еще раз — на мой взгляд, хуки вам не нужны. Все, что нужно — написать inproc com сервер, который будет загружаться при открытии нужной вам формы. Вы же ведь можете при ее открытии выполнять скрипт?
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[8]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 12.09.05 14:57
Оценка: +1
Здравствуйте, Ovl, Вы писали:

Ovl>Здравствуйте, Votblin, Вы писали:


V>>Здравствуйте, Ovl, Вы писали:


Ovl>>>Здравствуйте, Votblin, Вы писали:


V>>>>И что, действительно я смогу отловить нажатую клавишу для определенного контрола?


V>>>>ДА и непонятно как юзать этот SetWindowsHook(...)


V>>>>Не мотгли бы Вы подкинуть козу учитывая вышеприведенный код?


V>>>>Не бросайте на произвол ламера!


Ovl>>>не знаю что такое коза. но вот примеры из мсдн.

Ovl>>>Using Hooks

V>>А Вы уверены, что я перехвачу нажатие кнопки именно для определенного контрола (см. вышеприведенный код) ?


Ovl>сообщение о нажатии кнопки отправляется окну, например кнопка в общем случае — это тоже окно

Ovl>какому именно — можно определить по hwnd. соответственно сообщения для всех остальных окон — можно пропускать

плохо написал....

ловятся сообщения для всех окон в системе. ваше дело — отфильтровать не нужные.
к примеру
пришло сообщение окну hWnd, вызывается ваша хук-процедура.
смотрите у него parent window, если это "CVotBlinTable", то hWnd — ваш клиент. в противном случае — просто вызываете следующий хук вызовом CallNextHookProc
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Я в шоке GetMessage()
От: Votblin  
Дата: 12.09.05 11:32
Оценка:
Если я не туда запостил, плиз расскажите куда нужно таки?

Юзаем С++ в Visual Studio .NET

вот кусочек кода.

BOOL bRet = true;
MSG msg;
bRet = GetMessage(&msg, NULL, 0, 0);

Дело в том, что у меня GetMessage(&msg, NULL, 0, 0) не возвращает никакого значение.
Т.е. такое впечатление, будто прога зашла куда в глубины GetMessage() и там гдето зациклилось.

Чем лечить? В чем правда?

12.09.05 15:34: Перенесено модератором из 'Этюды для программистов' — Кодт
Re: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 12.09.05 11:38
Оценка:
Здравствуйте, Votblin, Вы писали:

V>Если я не туда запостил, плиз расскажите куда нужно таки?


V>Юзаем С++ в Visual Studio .NET


V>вот кусочек кода.


V>BOOL bRet = true;

V>MSG msg;
V>bRet = GetMessage(&msg, NULL, 0, 0);

V>Дело в том, что у меня GetMessage(&msg, NULL, 0, 0) не возвращает никакого значение.

V>Т.е. такое впечатление, будто прога зашла куда в глубины GetMessage() и там гдето зациклилось.

V>Чем лечить? В чем правда?




The GetMessage function retrieves a message from the calling thread's message queue. The function dispatches incoming sent messages until a posted message is available for retrieval.


то есть она возвращается, только когда в очереди сообщений что-то появляется — операция синхронная.
проверить, есть ли что-нибдуь в очереди можно функцией PeekMessage
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re: Я в шоке GetMessage()
От: Кодт Россия  
Дата: 12.09.05 11:42
Оценка:
Здравствуйте, Votblin, Вы писали:

V>Если я не туда запостил, плиз расскажите куда нужно таки?


Уж всяко не в Этюды. Ладно, спишем на панику.

V>BOOL bRet = true;
V>MSG msg;
V>bRet = GetMessage(&msg, NULL, 0, 0);

V>Дело в том, что у меня GetMessage(&msg, NULL, 0, 0) не возвращает никакого значение.
V>Т.е. такое впечатление, будто прога зашла куда в глубины GetMessage() и там гдето зациклилось.

V>Чем лечить? В чем правда?


Правда в документации. (А сила, брат, она в ньютонах).
GetMessage

GetMessage ждёт появления виндовских сообщений в очереди сообщений текущего потока, и когда дожидается — извлекает очередное сообщение и возвращает false (если это сообщение было WM_QUIT) либо true (во всех остальных случаях).

Причём программа не циклится в недрах системы, а висит на ожидании. Т.е. прервать (break) этот поток отладчиком не получится.

Если хочешь проверить, не ожидая — пожалуйста: PeekMessage.
Перекуём баги на фичи!
Re[2]: Я в шоке GetMessage()
От: Votblin  
Дата: 12.09.05 14:04
Оценка:
ОК ОК спасибо а разъяснения. Однако вот что пишу тогда:
В главной процедуре консольного приложения:

HWND hwnd;
char p[255];
while(1)
{
hwnd = ::FindWindow("CVotBlinTable", NULL);// GetWindow(hwnd,GW_HWNDNEXT);
::EnumChildWindows(hwnd,EnumChildProc, NULL);
}

и функция:


BOOL CALLBACK EnumChildProc(HWND hwndChild, LPARAM lParam)
{
char p[255];
::GetClassName(hwndChild, p, 1024);

if( strstr(p, "CGrid") &&
::IsWindowVisible(hwndChild) &&
::IsWindowEnabled(hwndChild)
)
{
BOOL bRet = true;
MSG msg;

while(PeekMessage(&msg, 0, 0, 0, PM_REMOVE))
{
if(msg.message == WM_QUIT)
cout << "Closing..." << endl;
else if(msg.message == WM_KEYUP)
cout << "KEY UP..." << endl;
else
cout << msg.message << endl;
TranslateMessage(&msg);
DispatchMessage(&msg);
cout << msg.message << endl;
}
}
return true;
}


Пояснения: СGrid — это грид — контрол т.е.

Нужно мне отоловить нажатие клавиш. А именно была ли нажата и код клавиши.

Спасибо заранее. не клюйте меня, ламера, плиз.
Re[3]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 12.09.05 14:12
Оценка:
Здравствуйте, Votblin, Вы писали:


отловить — помогут хуки

SetWindowsHook() или SetWindowsHookEx() с флагом WH_KEYBOARD

хотя возможно предложат способ проще....
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[4]: Я в шоке GetMessage()
От: Votblin  
Дата: 12.09.05 14:19
Оценка:
И что, действительно я смогу отловить нажатую клавишу для определенного контрола?

ДА и непонятно как юзать этот SetWindowsHook(...)

Не мотгли бы Вы подкинуть козу учитывая вышеприведенный код?

Не бросайте на произвол ламера!
Re[5]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 12.09.05 14:31
Оценка:
Здравствуйте, Votblin, Вы писали:

V>И что, действительно я смогу отловить нажатую клавишу для определенного контрола?


V>ДА и непонятно как юзать этот SetWindowsHook(...)


V>Не мотгли бы Вы подкинуть козу учитывая вышеприведенный код?


V>Не бросайте на произвол ламера!


не знаю что такое коза. но вот примеры из мсдн.
Using Hooks
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[6]: Я в шоке GetMessage()
От: Votblin  
Дата: 12.09.05 14:41
Оценка:
Здравствуйте, Ovl, Вы писали:

Ovl>Здравствуйте, Votblin, Вы писали:


V>>И что, действительно я смогу отловить нажатую клавишу для определенного контрола?


V>>ДА и непонятно как юзать этот SetWindowsHook(...)


V>>Не мотгли бы Вы подкинуть козу учитывая вышеприведенный код?


V>>Не бросайте на произвол ламера!


Ovl>не знаю что такое коза. но вот примеры из мсдн.

Ovl>Using Hooks

А Вы уверены, что я перехвачу нажатие кнопки именно для определенного контрола (см. вышеприведенный код) ?
Re[7]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 12.09.05 14:51
Оценка:
Здравствуйте, Votblin, Вы писали:

V>Здравствуйте, Ovl, Вы писали:


Ovl>>Здравствуйте, Votblin, Вы писали:


V>>>И что, действительно я смогу отловить нажатую клавишу для определенного контрола?


V>>>ДА и непонятно как юзать этот SetWindowsHook(...)


V>>>Не мотгли бы Вы подкинуть козу учитывая вышеприведенный код?


V>>>Не бросайте на произвол ламера!


Ovl>>не знаю что такое коза. но вот примеры из мсдн.

Ovl>>Using Hooks

V>А Вы уверены, что я перехвачу нажатие кнопки именно для определенного контрола (см. вышеприведенный код) ?


сообщение о нажатии кнопки отправляется окну, например кнопка в общем случае — это тоже окно
какому именно — можно определить по hwnd. соответственно сообщения для всех остальных окон — можно пропускать
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[9]: Я в шоке GetMessage()
От: Votblin  
Дата: 12.09.05 15:39
Оценка:
Спасибо за ответ. Но чтот я и та ки сяк пытался поюзать этот хук. Ничего не выходит.

МОжет подскажете все таки?
Re[9]: Я в шоке GetMessage()
От: Votblin  
Дата: 12.09.05 15:46
Оценка:
И насколько я понял из описания необходимо создавать dll.

Неужто все так запущено?
Re[3]: Я в шоке GetMessage()
От: Votblin  
Дата: 12.09.05 15:48
Оценка:
Это конечно все хорошо, но как отловить мессагу и ка копределить код клавиши для отловленного HANDLE окна?
Re[4]: Я в шоке GetMessage()
От: Andrew S Россия http://alchemy-lab.com
Дата: 12.09.05 15:54
Оценка:
V>Это конечно все хорошо, но как отловить мессагу и ка копределить код клавиши для отловленного HANDLE окна?

Сформулируйте поставленную вам задачу по-человечески Скажите, что вам нужно, и вам скажут, как это сделать.
http://www.rsdn.ru/Info/Howtoask.xml

В правильно поставленном вопросе содержится 50% ответа.

http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[5]: Я в шоке GetMessage()
От: Votblin  
Дата: 12.09.05 19:33
Оценка:
Конечно, конечно!

Вот собственно, та задача.

У нас есть какая то программка (конечно же без source code). Или даже так: у нас есть 1с v8.0.

И проблема в том, что в табличной части формы спика документов не отлавливается нажатие клавиш. Чтобы их все-таки отловить, я пытаюсь "споймать" message нужного окна.

Т.о. я сначалаи выискиваю handle этого окна, а далее пытаюсь с этого найденного окна словить сообщение ну пусть WM_CHAR. В конце концов, SPY++ ведь это както делает!

Вот собственно и задача.
Re[6]: Я в шоке GetMessage()
От: Andrew S Россия http://alchemy-lab.com
Дата: 12.09.05 19:56
Оценка:
V>У нас есть какая то программка (конечно же без source code). Или даже так: у нас есть 1с v8.0.
V>И проблема в том, что в табличной части формы спика документов не отлавливается нажатие клавиш. Чтобы их все-таки отловить, я пытаюсь "споймать" message нужного окна.
V>Т.о. я сначалаи выискиваю handle этого окна, а далее пытаюсь с этого найденного окна словить сообщение ну пусть WM_CHAR. В конце концов, SPY++ ведь это както делает!

Вы это пытаетесь делать извне или из inproc com сервера, например? Если извне, то, как уже тут говорили, на первый взгляд только хук + сабклассинг поможет. Вкратце технология была уже описана. Используем глобальный хук (например, shell или cbt), внедряемся в целевое приложение, загружаем dll, в которой будет наша процедура сабклассинга, сабклассируем. Можно, конечно, просто глобальный хук на WNDPROC или клавиатуру, но описанная выше методика гораздо более кошерна. Но все равно, и тот, и тот вариант — это как удалять гланды через анус. Лучше написать com расширение для 1c, загружать его из скрипта и из него сабклассировать окно. Это будет и переносимо, и без каких-либо хаков.
Пример можно посмотреть тут: http://gzip.rsdn.ru/article/dotnet/cs1c.xml
Автор(ы): Алексей Столповских
Дата: 20.11.2004
Данная статья описывает технологию создания COM+-компонента для 1С на C#. Код компонента был написан с использованием Microsoft Visual Studio.NET 2003, классов Microsoft .NET Framework 1.1 и протестирован на операционной системе Windows Server 2003 System.




В общем, главное попасть в адресное пространство 1с. А уж там перехватить\обработать нужные сообщения проблем не будет. Кстати, наверняка для нужного вам контрола есть и более легальные варианты, чем сабклассирование. Может, стоит спросить на специализированном форуме?
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[7]: Я в шоке GetMessage()
От: Votblin  
Дата: 12.09.05 21:22
Оценка:
Здравствуйте, Andrew S, Вы писали:

V>>У нас есть какая то программка (конечно же без source code). Или даже так: у нас есть 1с v8.0.

V>>И проблема в том, что в табличной части формы спика документов не отлавливается нажатие клавиш. Чтобы их все-таки отловить, я пытаюсь "споймать" message нужного окна.
V>>Т.о. я сначалаи выискиваю handle этого окна, а далее пытаюсь с этого найденного окна словить сообщение ну пусть WM_CHAR. В конце концов, SPY++ ведь это както делает!

AS>Вы это пытаетесь делать извне или из inproc com сервера, например? Если извне, то, как уже тут говорили, на первый взгляд только хук + сабклассинг поможет. Вкратце технология была уже описана. Используем глобальный хук (например, shell или cbt), внедряемся в целевое приложение, загружаем dll, в которой будет наша процедура сабклассинга, сабклассируем. Можно, конечно, просто глобальный хук на WNDPROC или клавиатуру, но описанная выше методика гораздо более кошерна. Но все равно, и тот, и тот вариант — это как удалять гланды через анус. Лучше написать com расширение для 1c, загружать его из скрипта и из него сабклассировать окно. Это будет и переносимо, и без каких-либо хаков.

AS>Пример можно посмотреть тут: http://gzip.rsdn.ru/article/dotnet/cs1c.xml
Автор(ы): Алексей Столповских
Дата: 20.11.2004
Данная статья описывает технологию создания COM+-компонента для 1С на C#. Код компонента был написан с использованием Microsoft Visual Studio.NET 2003, классов Microsoft .NET Framework 1.1 и протестирован на операционной системе Windows Server 2003 System.




AS>В общем, главное попасть в адресное пространство 1с. А уж там перехватить\обработать нужные сообщения проблем не будет. Кстати, наверняка для нужного вам контрола есть и более легальные варианты, чем сабклассирование. Может, стоит спросить на специализированном форуме?


Уважаемый, я в 1с кручусь уже 6 лет, так что поверьте — не поможет обращение в другие форумы. А то что Вы написали не совсем мне понятно, поскольку в с++ я не такой уж мастак осоебнно в WinAPI.

А прмерчик гляну обязательно, но уже утром пожалуй — спать пора!
Re[8]: Я в шоке GetMessage()
От: Andrew S Россия http://alchemy-lab.com
Дата: 12.09.05 21:35
Оценка:
AS>>В общем, главное попасть в адресное пространство 1с. А уж там перехватить\обработать нужные сообщения проблем не будет. Кстати, наверняка для нужного вам контрола есть и более легальные варианты, чем сабклассирование. Может, стоит спросить на специализированном форуме?

V>Уважаемый, я в 1с кручусь уже 6 лет, так что поверьте — не поможет обращение в другие форумы. А то что Вы написали не совсем мне понятно, поскольку в с++ я не такой уж мастак осоебнно в WinAPI.


В то, что обращение в другие форумы, специализированные под 1с, не поможет — я не верю. Лично я знаю ребят, которые с 1с могут сделать все что угодно.
Ну а касательно выделенной фразы — а что вы ждали? Готового кода? И каким образом С++ связано с WinApi, уже не понимаю я
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[9]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 04:59
Оценка:
AS>В то, что обращение в другие форумы, специализированные под 1с, не поможет — я не верю. Лично я знаю ребят, которые с 1с могут сделать все что угодно.

Не верьте, это Ваше дело. Но, проверно, а вот в это поверьте. Самое интересное, что фича с быстрым поиском документов в 1с 77 была. Но в 1с 8.0 с целью улучшения производительности исчезла в том виде, что была в 1с 7.7. Однако что в 1с77 что в 1с80 нет функции, которая реагирует на нажатие клавиатуры. С героической фирмы ABBYY я слышал лишь только слабые повякивания, смысл которых сводился сначала в кпроверки а лицензионная у меня 1с, потом лицензионный у меня виндовз, а потом что у меня за конфйигурация (УТ, УПП, или еще что нибудь, причем не дай Бог самописная!). Вот и два месяца назад я договорился аж получить наконецто диск ИТС, который так до сих пор и не пришел... Так что, то что касается франче — тема больная. Ну а то что, 1с-ки действительно на все руки мастера — это често, особенно не которые работают о франчах, а фикси. Ибо во франчах человек в-основном занят внедрением, а фикси или фрилансер — он занят разработкой конкретной.

Относительно статьи. Я, конечно, может и ошибаюсь, но она меня не совсем устраивает. Я писал конечно длл компоненты для 1с на си шарпе, но на другой фирме. А здесь это сделать нелегко. У нас около 30 филиалов разбросаных по Украине. и устанавливать на кждом по .NET Framework не сахар . Кроме того, есть калькуляторы, у которых установлено Вынь 98. А всего этих компьютеров насчитывается около 150 штук!

Неужто придется выбирать вариант "удалять гланды через анус"?

Вот еще одна статья: http://www.codeguru.com/Cpp/W-P/system/keyboard/article.php/c5699/ . Вот только мне не виртся, что получив HANDLE окна я не могу достучаться до WM_CHAR этого окна и получить код символа. В вышописанной статье путь конечно супер гиморный. Может посоветуете билиотеки какие?
Re[11]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 06:45
Оценка:
Ну создам я очередную компоненту, что тогда делать то? Как перехватить?
Re[12]: Я в шоке GetMessage()
От: Andrew S Россия http://alchemy-lab.com
Дата: 13.09.05 06:48
Оценка:
V>Ну создам я очередную компоненту, что тогда делать то? Как перехватить?

Применить сабклассирование. Находите нужное окно, сабклассируете его, и в своей WNDPROC обрабатываете нужные сообщения.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[13]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 06:49
Оценка:
Здравствуйте, Andrew S, Вы писали:

V>>Ну создам я очередную компоненту, что тогда делать то? Как перехватить?


AS>Применить сабклассирование. Находите нужное окно, сабклассируете его, и в своей WNDPROC обрабатываете нужные сообщения.


ОК, Andrew S. Спасибо. Вы супер. сейчас попробую. Эхх...
Re[11]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 07:43
Оценка:
Здравствуйте, Andrew S, Вы писали:

V>>Относительно статьи. Я, конечно, может и ошибаюсь, но она меня не совсем устраивает. Я писал конечно длл компоненты для 1с на си шарпе, но на другой фирме. А здесь это сделать нелегко. У нас около 30 филиалов разбросаных по Украине. и устанавливать на кждом по .NET Framework не сахар . Кроме того, есть калькуляторы, у которых установлено Вынь 98. А всего этих компьютеров насчитывается около 150 штук!


AS>Нда, что делает с человеком занятие 1с. При чем тут Net? Там был показан способ создания Com сервера для 1c. С тем же успехом это можно сделать и на ATL.


а com на 98-ой есть? или патчитить калькуляторы?
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[10]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 07:54
Оценка:
Здравствуйте, Votblin, Вы писали:

V>И насколько я понял из описания необходимо создавать dll.


V>Неужто все так запущено?


да, dll. потому что она хорошо подходит для этой цели — её можно загрузить в процесс, и она содержит только функции
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[12]: Я в шоке GetMessage()
От: Andrew S Россия http://alchemy-lab.com
Дата: 13.09.05 07:56
Оценка:
AS>>Нда, что делает с человеком занятие 1с. При чем тут Net? Там был показан способ создания Com сервера для 1c. С тем же успехом это можно сделать и на ATL.

Ovl>а com на 98-ой есть? или патчитить калькуляторы?


Странный вопрос. Com есть на 95-х. 1с же активно использует ActiveX\Com объекты, насколько я помню по своему давнему опыту общения с этим сабпродуктом.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[13]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 08:54
Оценка:
Здравствуйте, Andrew S, Вы писали:

AS>>>Нда, что делает с человеком занятие 1с. При чем тут Net? Там был показан способ создания Com сервера для 1c. С тем же успехом это можно сделать и на ATL.


Ovl>>а com на 98-ой есть? или патчитить калькуляторы?


AS>Странный вопрос. Com есть на 95-х. 1с же активно использует ActiveX\Com объекты, насколько я помню по своему давнему опыту общения с этим сабпродуктом.


вопрос не странный. просто я не знаю когда именно появился ком, не думал, что это было до появления 98.
однако в msdn:


HRESULT CoInitialize(
LPVOID pvReserved
);


Windows NT/2000/XP: Requires Windows NT 3.1 or later.

Windows 95/98: Requires Windows 95 or later.

Header: Declared in objbase.h.

Library: Use ole32.lib.


а вот насчет activeX — интуиция мне подсказывает, что наличие activeX коррелирует с наличием IE4.0
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[14]: Я в шоке GetMessage()
От: Andrew S Россия http://alchemy-lab.com
Дата: 13.09.05 08:58
Оценка:
Ovl>а вот насчет activeX — интуиция мне подсказывает, что наличие activeX коррелирует с наличием IE4.0

Интуиция вас обманывает. Для начала неплохо разобраться, что такое ActiveX
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[11]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 08:59
Оценка:
поправка

// appUsingHook.cpp

typedef void ( *STARTHOOKPROC )( HMODULE );

void ApplicationSetHook() {

...
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[11]: Я в шоке GetMessage()
От: Andrew S Россия http://alchemy-lab.com
Дата: 13.09.05 09:00
Оценка:
Ovl>посмотрел я посты — действительно, хук + сабклассинг более верно.

Я думаю, не нужен там хук. 1c позволяет писать под себя плагины.
http://www.rusyaz.ru/pr — стараемся писАть по-русски
Re[12]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 09:03
Оценка:
Здравствуйте, Andrew S, Вы писали:

Ovl>>посмотрел я посты — действительно, хук + сабклассинг более верно.


AS>Я думаю, не нужен там хук. 1c позволяет писать под себя плагины.


тем проще. однако я из кода не видно, что написание хука труднее.

в любом случае — это один из альтернативных вариантов. не пригодится ему — пригодится другому..
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[15]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 09:04
Оценка:
Здравствуйте, Andrew S, Вы писали:

Ovl>>а вот насчет activeX — интуиция мне подсказывает, что наличие activeX коррелирует с наличием IE4.0


AS>Интуиция вас обманывает. Для начала неплохо разобраться, что такое ActiveX


да, неплохо бы...

хотя мне бы программировать научится — и то удачно
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[11]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 10:29
Оценка:
Супер! Ovl, Спасибо за науку. Не забуду мать родную! оченб поучительно.
Re[11]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 11:12
Оценка:
А что это за зверь такой DLL_EXPORT ? Где обитает?
Re[12]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 11:20
Оценка:
Здравствуйте, Votblin, Вы писали:

V>А что это за зверь такой DLL_EXPORT ? Где обитает?



#define DLL_EXPORT __declspec( dllexport )


и ещё нуно добавить в проект файл hookDll.def

LIBRARY HOOKDLL.DLL
EXPORTS
SetHook @1
ClearHook @2
CBTProc @3


проверить правильность dll можно с помощью утилитки depends.
она должна показать, что из dll экспортируется три функции с этими именами
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[13]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 11:23
Оценка:
ОК, а как родить lp ?

в

if ( lp->lpszClass != 0 && stricmp(lp->lpszClass, "WindowClassName") == 0 )
Re[14]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 11:26
Оценка:
Здравствуйте, Votblin, Вы писали:

V>ОК, а как родить lp ?


V>в


V> if ( lp->lpszClass != 0 && stricmp(lp->lpszClass, "WindowClassName") == 0 )


забыл
        case HCBT_CREATEWND: {
            LPCREATESTRUCT lp = (LPCREATESTRUCT) lParam;
            if ( lp->lpszClass != 0 && stricmp(lp->lpszClass, "WindowClassName") == 0 ) {


и соответственно вместо "WindowClassName" будет имя класса окна, поведение которого ты хочешь изменить
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[15]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 11:34
Оценка:
Все конечно здорово, вот только не понятно что находится в

SubсlassWindow( (HWND) wParam );

Наверно у Вас эта длл магическим образом скомпилировалась...
Re[16]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 13:25
Оценка:
Здравствуйте, Votblin, Вы писали:

V>Все конечно здорово, вот только не понятно что находится в


V>SubсlassWindow( (HWND) wParam );


V>Наверно у Вас эта длл магическим образом скомпилировалась...


Всё ясно... Видать обиделся....
Re[17]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 13:28
Оценка:
Здравствуйте, Votblin, Вы писали:

V>Здравствуйте, Votblin, Вы писали:


V>>Все конечно здорово, вот только не понятно что находится в


V>>SubсlassWindow( (HWND) wParam );


V>>Наверно у Вас эта длл магическим образом скомпилировалась...


V>Всё ясно... Видать обиделся....


скорее просто не заметил или пропустил
это функция есть в листингах ранее


void SubclassWindow( HWND hwnd ) {
    if ( oldProc == NULL ) {
        oldProc = SetClassLongPtr( hwnd, GCLP_WNDPROC, NewWndProc );
    }
}
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[18]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 13:40
Оценка:
Сори, янаверно тебя уже достал конкретно, но в

void SubclassWindow( HWND hwnd )
{
if ( oldProc == NULL )
{
oldProc = SetClassLongPtr( hwnd, GCLP_WNDPROC, NewWndProc );
}
}

Определенно тот не то с возращаемым параметром и третим параметром тоже
Re[19]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 13.09.05 13:50
Оценка:
Здравствуйте, Votblin, Вы писали:

V>Сори, янаверно тебя уже достал конкретно, но в


V>void SubclassWindow( HWND hwnd )

V>{
V> if ( oldProc == NULL )
V>{
V> oldProc = SetClassLongPtr( hwnd, GCLP_WNDPROC, NewWndProc );
V> }
V>}

V>Определенно тот не то с возращаемым параметром и третим параметром тоже


используйте явное приведение


oldProc = (WNDPROC) SetClassLongPtr( hwnd, GCLP_WNDPROC, (LONG_PTR) NewWndProc );
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[20]: Я в шоке GetMessage()
От: Votblin  
Дата: 13.09.05 14:12
Оценка:
ОК ! Вы конечно не сердитесь на меня. В конце я выложу полный рабочий код Думаю это будет правильно.

Но до рабочего кода почему то еще далеко
Re[21]: Я в шоке GetMessage()
От: Votblin  
Дата: 14.09.05 07:18
Оценка:
А как юзать эту длл теперь.

Важный момент...
Re[22]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 14.09.05 08:06
Оценка:
Здравствуйте, Votblin, Вы писали:

V>А как юзать эту длл теперь.


V>Важный момент...


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

зы. пришло письмецо — не от вас?
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
Re[23]: Я в шоке GetMessage()
От: Votblin  
Дата: 14.09.05 08:08
Оценка:
Здравствуйте, Ovl, Вы писали:

Ovl>Здравствуйте, Votblin, Вы писали:


V>>А как юзать эту длл теперь.


V>>Важный момент...


Ovl>загрузить LoadLibrary, получить адрес процедуры, после чего вызвать оттуда функцию SetHook.

Ovl>это я написал в листинге. смотри там внимательнее.

Ovl>зы. пришло письмецо — не от вас?


Да письмо пришло от меня. рад познакомиться.
Re[24]: Я в шоке GetMessage()
От: ExceptionGranted  
Дата: 15.09.05 13:31
Оценка:
Вав!!! Какая романтичная история с хуками и dll'ми! Гы-гы-гы, извините не удержал_со
Сам когда с этим возился
Если не трудно, напишите потом чем все это закончилось, а то я не люблю читать романы без хеппи-эндов, гы-гы-гы ...
Re[25]: Я в шоке GetMessage()
От: Ovl Россия  
Дата: 15.09.05 13:37
Оценка:
Здравствуйте, ExceptionGranted, Вы писали:

EG>Вав!!! Какая романтичная история с хуками и dll'ми! Гы-гы-гы, извините не удержал_со

EG>Сам когда с этим возился
EG>Если не трудно, напишите потом чем все это закончилось, а то я не люблю читать романы без хеппи-эндов, гы-гы-гы ...

хэппи энда не будет видимо
пример с CBT хуком у меня глючил
Read or Die!
Как правильно задавать вопросы
Как правильно оформить свой вопрос
Автор: anvaka
Дата: 15.05.06
 
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.