📄 message.c
字号:
if (pMsgQueue->dwState & (0x01 << slot))
break;
}
if (slot == DEF_NR_TIMERS) {
pMsgQueue->dwState &= ~QS_TIMER;
pthread_mutex_unlock (&pMsgQueue->lock);
}
else {
pMsg->hwnd = pMsgQueue->TimerOwner[slot];
pMsg->message = MSG_TIMER;
pMsg->wParam = pMsgQueue->TimerID[slot];
pMsg->lParam = 0;
pMsg->pAdd = NULL;
pMsgQueue->dwState &= ~(0x01 << slot);
pthread_mutex_unlock (&pMsgQueue->lock);
return 1;
}
}
// no message, wait again.
sem_wait (&pMsgQueue->wait);
goto checkagain;
return 1;
}
int GUIAPI ThrowAwayMessages (HWND hWnd)
{
PMSG pMsg;
PMSGQUEUE pMsgQueue;
PQMSG pQMsg;
PSYNCMSG pSyncMsg;
int nCount = 0;
int readpos;
if( !(pMsgQueue = GetMsgQueue(hWnd)) ) return ERR_INV_HWND;
pthread_mutex_lock (&pMsgQueue->lock);
if (pMsgQueue->pFirstNotifyMsg) {
pQMsg = pMsgQueue->pFirstNotifyMsg;
while (pQMsg) {
pMsg = &pQMsg->Msg;
if (pMsg->hwnd == hWnd
|| GetMainWindowPtrOfControl (pMsg->hwnd) == (PMAINWIN)hWnd) {
pMsg->hwnd = HWND_INVALID;
nCount ++;
}
pQMsg = pQMsg->next;
}
}
/* FIXME: notify the waiting window */
if (pMsgQueue->pFirstSyncMsg) {
pSyncMsg = pMsgQueue->pFirstSyncMsg;
while (pSyncMsg) {
pMsg = &pSyncMsg->Msg;
if (pMsg->hwnd == hWnd
|| GetMainWindowPtrOfControl (pMsg->hwnd) == (PMAINWIN)hWnd) {
pMsg->hwnd = HWND_INVALID;
nCount ++;
}
pSyncMsg = pSyncMsg->pNext;
}
}
readpos = pMsgQueue->readpos;
while (readpos != pMsgQueue->writepos) {
pMsg = pMsgQueue->msg + readpos;
if (pMsg->hwnd == hWnd
|| GetMainWindowPtrOfControl (pMsg->hwnd) == (PMAINWIN)hWnd) {
pMsg->hwnd = HWND_INVALID;
nCount ++;
}
readpos++;
if (readpos >= pMsgQueue->len)
readpos = 0;
}
pthread_mutex_unlock (&pMsgQueue->lock);
return nCount;
}
BOOL GUIAPI PeekPostMessage (PMSG pMsg, HWND hWnd, int iMsgFilterMin,
int iMsgFilterMax, UINT uRemoveMsg)
{
PMSGQUEUE pMsgQueue;
PMSG pPostMsg;
if( !(pMsgQueue = GetMsgQueue(hWnd)) ) return FALSE;
memset (pMsg, 0, sizeof(MSG));
if (pMsgQueue->dwState & QS_POSTMSG) {
pthread_mutex_lock (&pMsgQueue->lock);
if (pMsgQueue->readpos != pMsgQueue->writepos) {
pPostMsg = pMsgQueue->msg + pMsgQueue->readpos;
if (iMsgFilterMin == 0 && iMsgFilterMax == 0)
*pMsg = *pPostMsg;
else if (pPostMsg->message <= iMsgFilterMax &&
pPostMsg->message >= iMsgFilterMin)
*pMsg = *pPostMsg;
else {
pthread_mutex_unlock (&pMsgQueue->lock);
return FALSE;
}
pMsg->pAdd = NULL;
if (uRemoveMsg == PM_REMOVE) {
pMsgQueue->readpos++;
if (pMsgQueue->readpos >= pMsgQueue->len)
pMsgQueue->readpos = 0;
}
pthread_mutex_unlock (&pMsgQueue->lock);
return TRUE;
}
pthread_mutex_unlock (&pMsgQueue->lock);
}
return FALSE;
}
int GUIAPI PostMessage(HWND hWnd, int iMsg, WPARAM wParam, LPARAM lParam)
{
PMSGQUEUE pMsgQueue;
PMSG pMsg;
int sem_value;
if( !(pMsgQueue = GetMsgQueue(hWnd)) ) return ERR_INV_HWND;
pthread_mutex_lock (&pMsgQueue->lock);
if (iMsg == MSG_PAINT) {
pMsgQueue->dwState |= QS_PAINT;
goto goodret;
}
if ((pMsgQueue->writepos + 1) % pMsgQueue->len == pMsgQueue->readpos) {
pthread_mutex_unlock (&pMsgQueue->lock);
return ERR_QUEUE_FULL;
}
// Write the data and advance write pointer */
pMsg = &(pMsgQueue->msg[pMsgQueue->writepos]);
pMsg->hwnd = hWnd;
pMsg->message = iMsg;
pMsg->wParam = wParam;
pMsg->lParam = lParam;
pMsgQueue->writepos++;
if (pMsgQueue->writepos >= pMsgQueue->len) pMsgQueue->writepos = 0;
pMsgQueue->dwState |= QS_POSTMSG;
goodret:
pthread_mutex_unlock (&pMsgQueue->lock);
// Signal that the msg queue contains one more element for reading
sem_getvalue (&pMsgQueue->wait, &sem_value);
if (sem_value <= 0)
sem_post(&pMsgQueue->wait);
return ERR_OK;
}
int GUIAPI PostQuitMessage(HWND hWnd)
{
PMSGQUEUE pMsgQueue;
int sem_value;
if( !(pMsgQueue = GetMsgQueue(hWnd)) ) return ERR_INV_HWND;
pMsgQueue->dwState |= QS_QUIT;
// Signal that the msg queue contains one more element for reading
sem_getvalue (&pMsgQueue->wait, &sem_value);
if (sem_value <= 0)
sem_post(&pMsgQueue->wait);
return ERR_OK;
}
int GUIAPI PostSyncMessage(HWND hWnd, int msg, WPARAM wParam, LPARAM lParam)
{
PMSGQUEUE pMsgQueue;
SYNCMSG SyncMsg;
int sem_value;
if( !(pMsgQueue = GetMsgQueue(hWnd)) ) return ERR_INV_HWND;
// queue the sync message.
SyncMsg.Msg.hwnd = hWnd;
SyncMsg.Msg.message = msg;
SyncMsg.Msg.wParam = wParam;
SyncMsg.Msg.lParam = lParam;
SyncMsg.pNext = NULL;
sem_init (&SyncMsg.sem_handle, 0, 0);
pthread_mutex_lock (&pMsgQueue->lock);
if (pMsgQueue->pFirstSyncMsg == NULL) {
pMsgQueue->pFirstSyncMsg = pMsgQueue->pLastSyncMsg = &SyncMsg;
}
else {
pMsgQueue->pLastSyncMsg->pNext = &SyncMsg;
pMsgQueue->pLastSyncMsg = &SyncMsg;
}
pMsgQueue->dwState |= QS_SYNCMSG;
pthread_mutex_unlock (&pMsgQueue->lock);
// Signal that the msg queue contains one more element for reading
sem_getvalue (&pMsgQueue->wait, &sem_value);
if (sem_value <= 0)
sem_post(&pMsgQueue->wait);
// suspend until the message been handled.
sem_wait(&SyncMsg.sem_handle);
sem_destroy(&SyncMsg.sem_handle);
return SyncMsg.retval;
}
int GUIAPI SendMessage(HWND hWnd, int iMsg, WPARAM wParam, LPARAM lParam)
{
WNDPROC WndProc;
PMAINWIN pMainWin;
if (hWnd == HWND_INVALID) return -1;
if (hWnd == HWND_DESKTOP) {
if (pthread_self() != __mg_desktop)
return PostSyncMessage (HWND_DESKTOP, iMsg, wParam, lParam);
else
return DesktopWinProc (hWnd, iMsg, wParam, lParam);
}
pMainWin = GetMainWindowPtrOfControl (hWnd);
if (pMainWin->th != pthread_self())
return PostSyncMessage (hWnd, iMsg, wParam, lParam);
WndProc = GetWndProc(hWnd);
return (*WndProc)(hWnd, iMsg, wParam, lParam);
}
int GUIAPI SendNotifyMessage(HWND hWnd, int iMsg, WPARAM wParam, LPARAM lParam)
{
// PMAINWIN pMainWin;
PMSGQUEUE pMsgQueue;
PQMSG pqmsg;
int sem_value;
if (hWnd == HWND_INVALID) return -1;
if( !(pMsgQueue = GetMsgQueue(hWnd)) ) return ERR_INV_HWND;
/*
if (hWnd == HWND_DESKTOP) {
if (pthread_self() == __mg_desktop)
return DesktopWinProc (hWnd, iMsg, wParam, lParam);
}
else {
pMainWin = GetMainWindowPtrOfControl (hWnd);
if (pMainWin->th == pthread_self()) {
WNDPROC WndProc;
WndProc = GetWndProc(hWnd);
return (*WndProc)(hWnd, iMsg, wParam, lParam);
}
}
*/
pqmsg = QMSGAlloc();
pthread_mutex_lock (&pMsgQueue->lock);
// queue the sync message.
pqmsg->Msg.hwnd = hWnd;
pqmsg->Msg.message = iMsg;
pqmsg->Msg.wParam = wParam;
pqmsg->Msg.lParam = lParam;
pqmsg->next = NULL;
if (pMsgQueue->pFirstNotifyMsg == NULL) {
pMsgQueue->pFirstNotifyMsg = pMsgQueue->pLastNotifyMsg = pqmsg;
}
else {
pMsgQueue->pLastNotifyMsg->next = pqmsg;
pMsgQueue->pLastNotifyMsg = pqmsg;
}
pMsgQueue->dwState |= QS_NOTIFYMSG;
pthread_mutex_unlock (&pMsgQueue->lock);
// Signal that the msg queue contains one more element for reading
sem_getvalue (&pMsgQueue->wait, &sem_value);
if (sem_value <= 0)
sem_post(&pMsgQueue->wait);
return ERR_OK;
}
int GUIAPI SendAsyncMessage(HWND hWnd, int iMsg, WPARAM wParam, LPARAM lParam)
{
WNDPROC WndProc;
if (hWnd == HWND_INVALID) return -1;
WndProc = GetWndProc(hWnd);
return (*WndProc)(hWnd, iMsg, wParam, lParam);
}
#ifdef _TRACE_MSG
int GUIAPI DispatchMessage(PMSG pMsg)
{
WNDPROC WndProc;
PSYNCMSG pSyncMsg;
int iRet;
fprintf (stderr, "Message, %s: hWnd: %x, wP: %x, lP: %lx. %s\n",
Message2Str (pMsg->message),
pMsg->hwnd,
pMsg->wParam,
pMsg->lParam,
pMsg->pAdd?"Sync":"Normal");
if (pMsg->hwnd == HWND_INVALID) {
if (pMsg->pAdd) {
pSyncMsg = (PSYNCMSG)pMsg->pAdd;
pSyncMsg->retval = HWND_INVALID;
sem_post(&pSyncMsg->sem_handle);
}
fprintf (stderr, "Message have been thrown away: %s\n",
Message2Str (pMsg->message));
return HWND_INVALID;
}
WndProc = GetWndProc (pMsg->hwnd);
if ( pMsg->pAdd ) // this is a sync message.
{
pSyncMsg = (PSYNCMSG)pMsg->pAdd;
pSyncMsg->retval = (*WndProc)
(pMsg->hwnd, pMsg->message, pMsg->wParam, pMsg->lParam);
sem_post(&pSyncMsg->sem_handle);
iRet = pSyncMsg->retval;
}
else
iRet = (*WndProc)(pMsg->hwnd, pMsg->message, pMsg->wParam, pMsg->lParam);
fprintf (stderr, "Message, %s done, return value: %x\n",
Message2Str (pMsg->message),
iRet);
return iRet;
}
#else
int GUIAPI DispatchMessage(PMSG pMsg)
{
WNDPROC WndProc;
PSYNCMSG pSyncMsg;
if (pMsg->hwnd == HWND_INVALID) {
if (pMsg->pAdd) {
pSyncMsg = (PSYNCMSG)pMsg->pAdd;
pSyncMsg->retval = HWND_INVALID;
sem_post(&pSyncMsg->sem_handle);
}
return HWND_INVALID;
}
WndProc = GetWndProc(pMsg->hwnd);
if ( pMsg->pAdd ) // this is a sync message.
{
pSyncMsg = (PSYNCMSG)pMsg->pAdd;
pSyncMsg->retval = (*WndProc)
(pMsg->hwnd, pMsg->message, pMsg->wParam, pMsg->lParam);
sem_post(&pSyncMsg->sem_handle);
return pSyncMsg->retval;
}
return (*WndProc)(pMsg->hwnd, pMsg->message, pMsg->wParam, pMsg->lParam);
}
#endif /* !TRACE_MSG */
#endif /* !LITE_VERSION */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -