// 重载设置控件隐藏状态的函数,需要调用子控件的函数 void CDuiPanel::SetControlHide(BOOL bIsHide) { __super::SetControlHide(bIsHide); // 设置每个子控件的原生Windows控件的可见性 for (size_t i = 0; i < m_vecControl.size(); i++) { CControlBase * pControlBase = m_vecControl.at(i); if (pControlBase) { if(pControlBase->IsClass(_T("div")) || pControlBase->IsClass(_T("tabctrl")) || pControlBase->IsClass(_T("layout"))) { // 如果子控件是容器类型控件,则调用子控件的设置隐藏函数 pControlBase->SetControlHide(bIsHide); }else { // 判断子控件当前是否可见,根据可见性设置子控件的原生控件的可见性 pControlBase->SetControlWndVisible(pControlBase->GetVisible()); } } } // 如果有插件,则设置插件的显示状态(插件接口暂不支持SetHide函数) if(m_pDuiPluginObject) { m_pDuiPluginObject->SetVisible(!bIsHide); } }
// 重载设置控件可见性的函数,需要调用子控件的函数 void CDuiPanel::SetControlVisible(BOOL bIsVisible) { __super::SetControlVisible(bIsVisible); // 设置每个子控件的原生Windows控件的可见性 for (size_t i = 0; i < m_vecControl.size(); i++) { CControlBase * pControlBase = m_vecControl.at(i); if (pControlBase) { if(pControlBase->IsClass(_T("div")) || pControlBase->IsClass(_T("tabctrl"))) { pControlBase->SetControlVisible(bIsVisible); }else { // Panel可见性变化时候,只会隐藏原生控件,不主动显示原生控件 //if(!bIsVisible) { pControlBase->SetControlWndVisible(bIsVisible); } } } } if(m_pDuiPluginObject) { m_pDuiPluginObject->SetVisible(bIsVisible); } }
// 重载设置控件可见性的函数,需要调用子控件的函数 void CDuiPanel::SetControlVisible(BOOL bIsVisible) { __super::SetControlVisible(bIsVisible); // 设置每个子控件的原生Windows控件的可见性 for (size_t i = 0; i < m_vecControl.size(); i++) { CControlBase * pControlBase = m_vecControl.at(i); if (pControlBase) { if(pControlBase->IsClass(_T("div")) || pControlBase->IsClass(_T("tabctrl")) || pControlBase->IsClass(_T("layout"))) { // 如果子控件是容器类型控件,则调用子控件的设置可见性函数 pControlBase->SetControlVisible(bIsVisible); }else { // 判断子控件当前是否可见,根据可见性设置子控件的原生控件的可见性 // 如果是edit控件,暂时不显示原生控件,否则tab页切换时候会有问题 BOOL bVisible = pControlBase->GetVisible(); if(pControlBase->IsClass(CDuiEdit::GetClassName())) { bVisible = FALSE; } pControlBase->SetControlWndVisible(bVisible); } } } // 如果有插件,则设置插件的可见性 if(m_pDuiPluginObject) { m_pDuiPluginObject->SetVisible(bIsVisible); } }
// 初始化窗口控件 void CDuiPanel::InitUI(CRect rcClient, DuiXmlNode pNode) { CRect rcTemp; int nStartX = 0; int nStartY = 0; CControlBase * pControlBase = NULL; // 加载所有窗口控件 if(pNode) { m_nVirtualHeight = 0; m_nVirtualWidth = 0; for (DuiXmlNode pControlElem = pNode.first_child(); pControlElem; pControlElem=pControlElem.next_sibling()) { if(pControlElem != NULL) { CString strControlName = pControlElem.name(); CControlBase* pControl = _CreateControlByName(strControlName); if(pControl) { pControl->Load(pControlElem); if(pControl->IsClass(CArea::GetClassName()) || pControl->IsClass(CDuiFrame::GetClassName())) { // Area和Frame不能响应鼠标,必须加到Area列表中 m_vecArea.push_back(pControl); }else { m_vecControl.push_back(pControl); } CRect rcCtrl = pControl->GetRect(); if(rcCtrl.bottom > m_nVirtualHeight) { m_nVirtualHeight = rcCtrl.bottom - m_rc.top; } if(rcCtrl.right > m_nVirtualWidth) { m_nVirtualWidth = rcCtrl.right - m_rc.left; } } } } // 需要的总高度大于显示区高度才会显示垂直滚动条 m_pControScrollV->SetVisible(m_nVirtualHeight > m_rc.Height()); ((CDuiScrollVertical*)m_pControScrollV)->SetScrollMaxRange(m_nVirtualHeight); // 需要的总宽度大于显示区宽度才会显示垂直滚动条 m_pControScrollH->SetVisible(m_nVirtualWidth > m_rc.Width()); ((CDuiScrollHorizontal*)m_pControScrollH)->SetScrollMaxRange(m_nVirtualWidth); } m_bInit = true; }
// 加载XML节点中定义的菜单和其他控件 BOOL CDuiMenu::LoadXmlNode(TiXmlElement* pXmlElem, CString strXmlFile) { if(pXmlElem == NULL) { return FALSE; } TiXmlElement* pControlElem = NULL; for (pControlElem = pXmlElem->FirstChildElement(); pControlElem != NULL; pControlElem=pControlElem->NextSiblingElement()) { if(pControlElem != NULL) { CStringA strControlName = pControlElem->Value(); CControlBase* pControl = _CreateControlByName(strControlName); if(pControl) { if(pControl->Load(pControlElem)) { // 如果Load成功,则添加控件 if(pControl->IsClass(CArea::GetClassName()) || pControl->IsClass(CFrame::GetClassName())) { // Area和Frame不能响应鼠标,必须加到Area列表中 m_vecArea.push_back(pControl); }else { m_vecControl.push_back(pControl); } // 如果是菜单项控件,则设置菜单项的菜单XML属性 if(pControl->IsClass(CMenuItem::GetClassName())) { ((CMenuItem*)pControl)->SetMenuXml(strXmlFile); } }else { // 否则直接删除控件对象指针 delete pControl; } } } } return TRUE; }
// 清除指定类型的子控件 void CControlBase::RemoveControls(CStringA strClassName) { for (int i = m_vecControl.size()-1; i >= 0; i--) { CControlBase* pControlBase = m_vecControl.at(i); if(pControlBase->IsClass(strClassName)) { RemoveControl(pControlBase); } } }
// 初始化窗口控件 void CDlgPopup::InitUI(CRect rcClient, DuiXmlNode pNode) { CRect rcTemp; int nStartX = 0; int nStartY = 0; CControlBase * pControlBase = NULL; // 加载所有窗口控件 if(pNode) { for (DuiXmlNode pControlElem = pNode.first_child(); pControlElem; pControlElem=pControlElem.next_sibling()) { if(pControlElem) { CString strControlName = pControlElem.name(); CControlBase* pControl = _CreateControlByName(strControlName); if(pControl) { if(pControl->Load(pControlElem)) { // 如果Load成功,则添加控件 if(pControl->IsClass(CArea::GetClassName()) || pControl->IsClass(CFrame::GetClassName())) { // Area和Frame不能响应鼠标,必须加到Area列表中 m_vecArea.push_back(pControl); }else { m_vecControl.push_back(pControl); } }else { // 否则直接删除控件对象指针 delete pControl; } } } } } m_bInit = true; }
// 消息响应 LRESULT CDuiMenu::OnMessage(UINT uID, UINT Msg, WPARAM wParam, LPARAM lParam) { if((Msg != MSG_BUTTON_UP) && (Msg != MSG_BUTTON_CHECK)) { return 0; } CControlBase* pControl = GetControl(uID); if(pControl && !pControl->GetAction().IsEmpty()) { // 如果菜单项设置了action,则添加到动作任务队列中,通过任务来执行 CString strControlName = pControl->GetName(); CString strAction = pControl->GetAction(); //CDuiObject* pParent = pControl->GetParent(); CDlgBase* pParentDlg = pControl->GetParentDialog(); DuiSystem::Instance()->AddDuiActionTask(uID, Msg, wParam, lParam, strControlName, strAction, pParentDlg); }else { // 否则就调用Popup的函数 __super::OnMessage(uID, Msg, wParam, lParam); /*tagMenuInfo* pMenuInfo = new tagMenuInfo; pMenuInfo->uMenuID = uID; pMenuInfo->bSelect = (bool)lParam; pMenuInfo->bDown = (bool)wParam; PostMessage(m_uMessageID, Msg, (LPARAM)pMenuInfo);*/ } if(Msg == MSG_BUTTON_UP) { // 如果点击的是弹出菜单,则不用关闭 if(pControl && pControl->IsClass(CMenuItem::GetClassName()) && ((CMenuItem*)pControl)->IsPopup()) { return 0; } // 如果有父菜单,将父菜单关闭,不采用直接关闭的方法,而是设置自动关闭标识,并通过鼠标事件触发自动关闭 CDuiMenu* pParentMenu = GetParentMenu(); if(pParentMenu && !pParentMenu->IsAutoClose()) { pParentMenu->SetAutoClose(TRUE); pParentMenu->SetForegroundWindow(); pParentMenu->PostMessage(WM_LBUTTONDOWN, 0, 0); } // 关闭自身 CloseWindow(); } return 0; }
// 加载XML节点中定义的菜单和其他控件 BOOL CDuiMenu::LoadXmlNode(DuiXmlNode pXmlElem, CString strXmlFile) { if(pXmlElem == NULL) { return FALSE; } for (DuiXmlNode pControlElem = pXmlElem.first_child(); pControlElem; pControlElem=pControlElem.next_sibling()) { CString strControlName = pControlElem.name(); CControlBase* pControl = _CreateControlByName(strControlName); if(pControl) { if(pControl->Load(pControlElem)) { // 如果Load成功,则添加控件 if(pControl->IsClass(CArea::GetClassName()) || pControl->IsClass(CDuiFrame::GetClassName())) { // Area和Frame不能响应鼠标,必须加到Area列表中 m_vecArea.push_back(pControl); }else { m_vecControl.push_back(pControl); } // 如果是菜单项控件,则设置菜单项的菜单XML属性 if(pControl->IsClass(CMenuItem::GetClassName())) { ((CMenuItem*)pControl)->SetMenuXml(strXmlFile); } }else { // 否则直接删除控件对象指针 delete pControl; } } } return TRUE; }
// 获取当前处于活动状态的子菜单项 CMenuItem* CDuiMenu::GetHoverMenuItem() { for (size_t i = 0; i < m_vecControl.size(); i++) { CControlBase * pControlBase = m_vecControl[i]; if(pControlBase->IsClass(CMenuItem::GetClassName())) // 如果是MenuItem类型控件 { CMenuItem* pMenuItem = (CMenuItem*)pControlBase; if(pMenuItem->IsHover()) { return pMenuItem; } } } return NULL; }
// 刷新父控件下面所有同一个组的RadioButton控件的状态 BOOL CMenuItem::ResetGroupCheck() { CDuiObject* pParentObj = GetParent(); if(pParentObj == NULL) { return FALSE; } vector<CControlBase*>* pvecControl = NULL; if(pParentObj->IsClass(_T("dlg"))) { CDlgBase* pDlg = static_cast<CDlgBase*>(pParentObj); pvecControl = pDlg->GetControls(); }else if(pParentObj->IsClass(_T("popup"))) { CDlgPopup* pDlg = static_cast<CDlgPopup*>(pParentObj); pvecControl = pDlg->GetControls(); }else { CControlBase* pControlBase = static_cast<CControlBase*>(pParentObj); pvecControl = pControlBase->GetControls(); } if(pvecControl == NULL) { return FALSE; } for(int i=0; i<(int)pvecControl->size(); i++) { CControlBase* pControlBase = pvecControl->at(i); if(pControlBase->IsClass(CMenuItem::GetClassName()) && pControlBase->GetVisible() && !pControlBase->GetDisable()) { CMenuItem* pControl = static_cast<CMenuItem*>(pControlBase); if((pControl->GetGroupName() == m_strGroupName) && (pControl != this)) { // 重置控件状态 pControl->SetControlCheck(FALSE); } } } return TRUE; }
// 获取当前处于活动状态的子菜单项(根据鼠标位置查找) CMenuItem* CDuiMenu::GetMenuItemWithPoint(CPoint point) { for (size_t i = 0; i < m_vecControl.size(); i++) { CControlBase * pControlBase = m_vecControl[i]; if(pControlBase->IsClass(CMenuItem::GetClassName())) // 如果是MenuItem类型控件 { CMenuItem* pMenuItem = (CMenuItem*)pControlBase; CRect rc = pMenuItem->GetRect(); if(rc.PtInRect(point)) { return pMenuItem; } } } return NULL; }
// 获取所在Radio组选择的控件的值 CString CMenuItem::GetGroupValue() { CDuiObject* pParentObj = GetParent(); if(pParentObj == NULL) { return _T(""); } vector<CControlBase*>* pvecControl = NULL; if(pParentObj->IsClass(_T("dlg"))) { CDlgBase* pDlg = static_cast<CDlgBase*>(pParentObj); pvecControl = pDlg->GetControls(); }else if(pParentObj->IsClass(_T("popup"))) { CDlgPopup* pDlg = static_cast<CDlgPopup*>(pParentObj); pvecControl = pDlg->GetControls(); }else { CControlBase* pControlBase = static_cast<CControlBase*>(pParentObj); pvecControl = pControlBase->GetControls(); } if(pvecControl == NULL) { return _T(""); } for(int i=0; i<(int)pvecControl->size(); i++) { CControlBase* pControlBase = pvecControl->at(i); if(pControlBase->IsClass(CMenuItem::GetClassName()) && pControlBase->GetVisible() && !pControlBase->GetDisable()) { CMenuItem* pControl = static_cast<CMenuItem*>(pControlBase); if((pControl->GetGroupName() == m_strGroupName) && pControl->GetCheck()) { return pControl->GetValue(); } } } return _T(""); }
// 设置菜单项位置 void CDuiMenu::SetMenuPoint() { int nXPos = 2; int nYPos = (m_nTopHeight != 0) ? m_nTopHeight : 2; CRect rc; for (size_t i = 0; i < m_vecControl.size(); i++) { CControlBase * pControlBase = m_vecControl[i]; if(pControlBase == NULL) { continue; } if(pControlBase->IsClass(CMenuItem::GetClassName())) // 如果是MenuItem类型控件 { CMenuItem* pMenuItem = (CMenuItem*)pControlBase; pMenuItem->SetFrameWidth(m_nFrameWidth); if(!pMenuItem->GetVisible()) { // 菜单项不可见 rc.SetRect(0,0,0,0); }else if(pMenuItem->IsSeparator()) { // 分隔线 rc.SetRect(m_nLeft + 1, nYPos + 1, m_nWidth - 1, nYPos + 2); nYPos += 4; }else { // 普通菜单项 rc.SetRect(nXPos, nYPos, m_nWidth - 2, nYPos + m_nHeight); nYPos += m_nHeight; // 设置菜单项的鼠标移动时候的背景 if(m_pImageRowHover != NULL) { pMenuItem->m_pImageHover = m_pImageRowHover; pMenuItem->m_sizeHover = m_sizeRowHover; }else { pMenuItem->m_clrHover = m_clrRowHover; // 设置菜单项的背景色 } // 设置菜单项的弹出菜单箭头图片 if(m_pImagePopupArrow != NULL) { pMenuItem->m_pImagePopupArrow = m_pImagePopupArrow; pMenuItem->m_sizePopupArrow = m_sizePopupArrow; } } SetControlRect(pControlBase, rc); }else if(-1 == pControlBase->GetControlID()) { rc.SetRect(m_nLeft + 4, nYPos + 1, m_nWidth - 9, nYPos + 2); nYPos += 4; SetControlRect(pControlBase, rc); } } nYPos += ((m_nBottomHeight != 0) ? m_nBottomHeight : 2); SetWindowPos(NULL, 0, 0, m_nWidth, nYPos, SWP_NOMOVE); SetRect(CRect(0, 0, m_nWidth, nYPos)); // 设置菜单窗口的大小 // 设置非菜单项控件的位置(必须在高度计算出来之后设置) for (size_t i = 0; i < m_vecControl.size(); i++) { CControlBase * pControlBase = m_vecControl[i]; if(pControlBase == NULL) { continue; } if(pControlBase->IsClass(CMenuItem::GetClassName())) { continue; }else if(-1 == pControlBase->GetControlID()) { continue; }else { pControlBase->OnAttributePosChange(pControlBase->GetPosStr(), FALSE); } } InvalidateRect(NULL); }