今天很自觉地把以前写的MMI对话程序优化了一下。
以前在CDigMMI::OnInitDialog里做了很多初始化工作,其中有些初始化还花费比较长的时间。这样的话,打开MMI窗口就会变得很慢,特别是跟MMI通信失败的情况下,整个窗口都挂死状态。
优化:当检测到CAM存在的时候设置个时钟,然后在时钟消息处理函数里检测什么时候MMI到来,到了后再KillTimer 及更新MMI 窗口控件列表的显示。
相当于把一些需要长时间等待的事情放到另外一个线程里做,这样的话就不会影响到主线程。MMI窗口的打开和关闭变得比较顺畅。
希望以后在动手写代码之前先仔细地想一想,稍微做一些规划及注重下效率。
顺便附上一点代码
BOOL CDigMMI::OnInitDialog()
{
CDialog::OnInitDialog();
UCHAR ucSetCmd[512];
UCHAR ucStatus[1024];
//if cam is available, set a timer to check if mmi arrived,then to fill dialog context.
if(TBS_CamStatus())
{
ucSetCmd[0]=PCMSG_ENTER_MENU;
TBS_ci_MMI_Pstatus(ucSetCmd,ucStatus);
SetTimer(1, 1000, NULL);
}
//initDisplayEdit();
return TRUE; // return TRUE unless you set the focus to a control
}
void CDigMMI::OnTimer(UINT_PTR nIDEvent)
{
OutputDebugString("********OnTimer ");
if(initDisplayEdit() != S_OK)
{
return;
}
else
{
KillTimer(1);
}
CDialog::OnTimer(nIDEvent);
}
void CDigMMI::OnBnClickedExit()
{
//initDisplayEdit();
UCHAR ucSetCmd[512];
UCHAR ucStatus[1024];
int i=0;
if(TBS_CamStatus())
{
ucSetCmd[0] = PCMSG_ENTER_MENU;
TBS_ci_MMI_Pstatus(ucSetCmd,ucStatus);
while((initDisplayEdit() != S_OK)&&(i<5))
{
i++;
Sleep(1000);
}
}
}
HRESULT CDigMMI::initDisplayEdit()
{
int i=0;
CString strMmiInfo;
UCHAR ucStatus[1024];
UCHAR ucSetCmd[512];
HRESULT hr = S_FALSE;
//for menu
int ilength =0;
int ichoiceNb =0;
CString strTitle;
CString strSubTitle;
CString strBottom;
CString strItem;
CString strTemp;
CString strItemNew;
int ipos=0;
int ilastpos=0;
CString strAppInfo;
// to_log
char buff[1024]="";
DWORD dwStyle;
dwStyle = m_editCmd.GetStyle();
// PCMSG_ANSWER
if(dwStyle & ES_PASSWORD)
{
// cancel password style
m_editCmd.SetPasswordChar(NULL);
}
ucSetCmd[0]=PCMSG_GET_MMI;
TBS_ci_MMI_Pstatus(ucSetCmd,ucStatus);
if(ucStatus[4] ==PCMSG_NULL)
return hr;
/*
for(i=0;i<5;i++)
{
if(ucStatus[4] !=PCMSG_NULL) // commandTag !=0
{
break;
}
Sleep(2000);
TBS_ci_MMI_Pstatus(ucSetCmd,ucStatus);
}
*/
// get mmi menu and analyze it then set infs to UI
if(ucStatus[4] ==PCMSG_MENU)
{
//get length
ilength = ucStatus[6]*256 + ucStatus[5];
//get choice_nb
ichoiceNb = ucStatus[7];
//get title text()
while((*(ucStatus+8+ipos)!=0)&&(ipos<ilength))
ipos++;
strTitle = ucStatus + 8;
ipos++;
//get sub-title text()
ilastpos=ipos;
while((*(ucStatus+8+ipos)!=0)&&(ipos<ilength))
ipos++;
strSubTitle = ucStatus + ilastpos+8;
ipos++;
//get bottom text()
ilastpos=ipos;
while((*(ucStatus+8+ipos)!=0)&&(ipos<ilength))
ipos++;
strBottom = ucStatus + ilastpos+8;
//get each choice_nb text
strItem ="";
for(int itext=0;itext<ichoiceNb;itext++)
{
ipos++;
for(ilastpos=ipos;ipos<ilength;ipos++)
{
if(*(ucStatus+8+ipos) ==0)
{
//strItem = ucStatus + ilastpos+8;
break;
}
}
strTemp.Format("%d",itext+1);
strItemNew = ucStatus + ilastpos+8;
strItem = strItem + strTemp +": "+ strItemNew +"/r/n";
}
// set menu infs to UI
m_textMain.SetWindowText(strTitle);
m_textSub.SetWindowText(strSubTitle);
m_textCmd.SetWindowText(strBottom);
m_editDisplay.SetWindowText(strItem);
}
// get application info
ucSetCmd[0]=PCMSG_APPLICATION_INFO;
for(int i=0;i<5;i++)
{
TBS_ci_MMI_Pstatus(ucSetCmd,ucStatus);
if(ucStatus[4] !=PCMSG_NULL) // commandTag !=0
{
break;
}
}
if(ucStatus[4] ==PCMSG_APPLICATION_INFO)
{
// application type
if(*(ucStatus+7)==0x01)
{
m_appType.SetWindowText("CA");
}
else if(*(ucStatus+7)==0x02)
{
m_appType.SetWindowText("EPG");
}
else
{
m_appType.SetWindowText("NA");
}
// application Info
strAppInfo = ucStatus+12;
m_appInfo.SetWindowText(strAppInfo);
}
return S_OK;
}