做了一个控件,在OleCtrl的OnCreate里创建了一个PropertySheet作为child,在propertysheet中加了3个page.
    在程序中加入该控件后,如果在一个模态对话框中,则对话框Domodal失败,程序不响应.
    如果在非模态对话框中,显示和使用正常,可是一旦调用控件的任意方法之后,控件就再也不响应了.
    别人告诉我这是跟我的控件的PreTranslateMessage有关,不知是不是这样.
    请高手帮忙,现在工作就要用啊!!!!!!!!!!!!!!!!!!!!!chat* bow................

解决方案 »

  1.   

    怎么没人回啊??难道没有人遇到这种情况吗???chat* dao
      

  2.   

    我还没有做过类似的工作.不过我知道类似的书<COM/DCOM编程指南>,需要的话...
      

  3.   

    template <class T, class TBase = CWindow>
    class ATL_NO_VTABLE CPropertyPageImpl : public CAxDialogImpl< T >
    {
      typedef CDialogImplBaseT< TBase > _DialogImplBaseClass;
      DLGTEMPLATE* m_pDlgTemplate;
    public:
      CPropertyPageImpl() throw()
      {
        AtlAxWinInit();
        HRSRC hDlg = AtlFindResource(_AtlBaseModule.GetResourceInstance(), MAKEINTRESOURCE(T::IDD), (LPCTSTR)RT_DIALOG);
        if (hDlg != NULL){
          DWORD dwLastError = 0;
          HGLOBAL hResource = LoadResource(_AtlBaseModule.GetResourceInstance(), hDlg);
          if (hResource != NULL){
            DLGTEMPLATE* pDlg = (DLGTEMPLATE*) LockResource(hResource);
            if (pDlg != NULL){
              m_pDlgTemplate = _DialogSplitHelper::SplitDialogTemplate(pDlg, NULL);
              return;}}}
        throw 0; }
      ~CPropertyPageImpl(){ ::GlobalFree(GlobalHandle(m_pDlgTemplate)); }
      BOOL InitPropSheetPage(PROPSHEETPAGE * psp, LPCTSTR lpTitleText = NULL, LPCTSTR lpIconResource = NULL)
      {
        psp->dwSize = sizeof(PROPSHEETPAGE);
        psp->dwFlags = PSP_USETITLE | PSP_DLGINDIRECT ;
        psp->hInstance = _AtlBaseModule.GetResourceInstance();
        psp->pResource = m_pDlgTemplate;
        psp->pszIcon = lpIconResource;
        psp->pfnDlgProc = StartPropertyPageProc;
        psp->lParam = (LPARAM)(_DialogImplBaseClass*)(this);
        psp->pszTitle = lpTitleText;
        psp->pfnCallback = NULL;
        return TRUE;
      }
      static INT_PTR CALLBACK StartPropertyPageProc(HWND hWnd, UINT uMsg, WPARAM wParam, LPARAM lParam){
        if(uMsg != WM_INITDIALOG){
          return ::DefWindowProc(hWnd, uMsg, wParam, lParam);
        }
        PROPSHEETPAGE * pStruct = (PROPSHEETPAGE*)lParam;
        _DialogImplBaseClass* pThis = (_DialogImplBaseClass*)pStruct->lParam;
        ATLASSERT(pThis != NULL);
        pThis->m_hWnd = hWnd;
        pThis->m_thunk.Init((WNDPROC)pThis->GetDialogProc(), (CDialogImplBaseT<TBase>*)pThis);
        DLGPROC pProc = (DLGPROC)pThis->m_thunk.GetWNDPROC();
        DLGPROC pOldProc = (DLGPROC)::SetWindowLongPtr(hWnd, DWLP_DLGPROC, (LONG_PTR)pProc);
      #ifdef _DEBUG
        // check if somebody has subclassed us already since we discard it
        if(pOldProc != StartPropertyPageProc)
          ATLTRACE(atlTraceWindowing, 0, _T("Subclassing through a hook discarded.\n"));
      #else
        pOldProc;  // avoid unused warning
      #endif
        return pProc(hWnd, uMsg, wParam, lParam);
      }
    };
      

  4.   

    class CPage1 : public CPropertyPageImpl<CPage1>
    {
      ..
    };
    class CPage2 : public CPropertyPageImpl<CPage2>
    {
      ..
    };
    extern "C" int WINAPI _tWinMain(HINSTANCE /*hInstance*/, HINSTANCE /*hPrevInstance*/, 
      LPTSTR /*lpCmdLine*/, int nShowCmd)
    {
      CPage1 page1;
      CPage2 page2;
      PROPSHEETPAGE psp[2];
      page1.InitPropSheetPage(psp, _T("Page1"));
      page2.InitPropSheetPage(psp + 1, _T("Page2"));
      PROPSHEETHEADER psh;
      psh.dwSize = sizeof(PROPSHEETHEADER);
      psh.dwFlags = PSH_PROPSHEETPAGE;
      psh.hwndParent = NULL;
      psh.hInstance = _AtlBaseModule.GetResourceInstance();
      psh.pszIcon = NULL;
      psh.pszCaption = (LPSTR) "Cell Properties";
      psh.nPages = sizeof(psp) / sizeof(PROPSHEETPAGE);
      psh.nStartPage = 0;
      psh.ppsp = (LPCPROPSHEETPAGE) &psp;
      psh.pfnCallback = NULL;
      PropertySheet(&psh);
      return 1;
    }
    这是用ATL创建支持ActiveX的PropertySheet的方法。给你参考一下。至于在OleCtrl里面创建作为自窗口的ProperSheet,估计是子窗口没有分离作为ActiveX的部分资源,因为CreateDialog,CreateDialogIndirect,DialogBox,DialogBoxIndirect等八个函数创建的对话框都只支持标准的Windows资源。所以你必须在调用前把不标准资源(包括ActiveX等)分离,然后用XXX-InDirect-XXX的API创建内存对话框,在对话框初始化消息处理时用CreateWindowEx把这些非标准资源添加到对话框上,CDialog,ATL::CAxDialogImpl就是这样包含了类似的工作。但是你说的把PropertySheet作为子窗口,就难说了,我很少用MFC,但是如果你把PropertySheet以及对话框的原理都清楚了,会很容易解决的。