Нужно создать новый поток, который отслеживал
бы изменения в файловой системе и обновлял
содержимое TreeView. Изменения ослеживаются
с помощью FindFirstChangeNotification и WaitForSingleObject.
Новый поток создаю с помощью AfxBeginThread().
Первый параметр — указатель на функцию, реализующую
поток. Вопрос в том, что если описать эту функцию как
член класса, из которого создаётся новый поток, то компилятор
выдаёт странную ошибку:
D:\Projects\WORK\NewThr\NewThrDlg.cpp(185) : error C2665: 'AfxBeginThread' :
none of the 2 overloads can convert parameter 1 from type 'unsigned int
(__thiscall CNewThrDlg::*)(void *)'
Но если описать эту функцию во внешнем h — файле, затем подключить его к
классу, создающему поток,
то поток создаётся нормально, но из этой функции невозможно вызвать метод
класса,
который обновляет содержимое TreeView:
AfxBeginThread(MyNewThread, &m_MyStruct);
...
UINT MyNewThread(LPVOID pParam)
{
....
Если здесь попытаться вызвать метод класса, создающего поток, то
получу ошибку типа:
D:\PROJECTS\WORK\Simpexp\FoldersView.cpp(518) : error C2352:
'FoldersView::FillFoldersTree' : illegal call of non-static member function
}
Вот такие вот дела...
Может есть какие мысли по этому поводу?
ЕЧ>Нужно создать новый поток, который отслеживал ЕЧ>бы изменения в файловой системе и обновлял ЕЧ>содержимое TreeView. Изменения ослеживаются ЕЧ>с помощью FindFirstChangeNotification и WaitForSingleObject.
ЕЧ>Новый поток создаю с помощью AfxBeginThread().
ЕЧ>Первый параметр — указатель на функцию, реализующую ЕЧ>поток. Вопрос в том, что если описать эту функцию как ЕЧ>член класса, из которого создаётся новый поток, то компилятор ЕЧ>выдаёт странную ошибку:
ЕЧ>void CNewThrDlg::OnOK() ЕЧ>{ ЕЧ>UINT (CNewThrDlg::*pFunction)(LPVOID pParam) = CNewThrDlg::MyNewThread; ЕЧ>AfxBeginThread(pFunction, &m_MyStruct); ЕЧ>}
ЕЧ>...
ЕЧ>UINT CNewThrDlg::MyNewThread(LPVOID pParam) ЕЧ>{ ЕЧ>AfxMessageBox("New thread started"); ЕЧ>return 0; ЕЧ>}
ЕЧ>При компиляции выдаётся сообщение:
ЕЧ>D:\Projects\WORK\NewThr\NewThrDlg.cpp(185) : error C2665: 'AfxBeginThread' : ЕЧ>none of the 2 overloads can convert parameter 1 from type 'unsigned int ЕЧ>(__thiscall CNewThrDlg::*)(void *)'
ЕЧ>Но если описать эту функцию во внешнем h — файле, затем подключить его к ЕЧ>классу, создающему поток, ЕЧ>то поток создаётся нормально, но из этой функции невозможно вызвать метод ЕЧ>класса, ЕЧ>который обновляет содержимое TreeView:
ЕЧ>AfxBeginThread(MyNewThread, &m_MyStruct);
ЕЧ>...
ЕЧ>UINT MyNewThread(LPVOID pParam) ЕЧ>{ ЕЧ>.... ЕЧ>Если здесь попытаться вызвать метод класса, создающего поток, то ЕЧ>получу ошибку типа: ЕЧ>D:\PROJECTS\WORK\Simpexp\FoldersView.cpp(518) : error C2352: ЕЧ>'FoldersView::FillFoldersTree' : illegal call of non-static member function ЕЧ>}
ЕЧ>Вот такие вот дела... ЕЧ>Может есть какие мысли по этому поводу?
ЕЧ>Thanks...
Все вполне просто объясняется. В любой член-функции первым параметром идет неявный указатель this, поэтому функция потока для компилятора выгладит примерно так void CMyClass::MyThread(CMyClass* this, LPVOID pParam), что немного отличается от функции потока :). Решение два.
1) Либо объявить член функцию класс(которая является функцией потока) типа static. Тогда в нее не будет передаваться неявный казатель this. Но обращять можно будет из нее, только к static член-функциям или член-данным.
2) Зделать функцию потока глобальной(Не член функцией класса).
В документации на MFC есть ограничение на использование в потоках классов производных от CObject
(в том числе и CWnd).
Чтобы использовать в разных потока одно окно диалога, нужно передать дочернему потоку Хэндл окна.
А в потоке вызвать CWnd::FromHandle(m_hWnd).
В твоём случае нужно сделать так: