📄 dsofcontrol.cpp
字号:
if (fModeless)
PostMessage(m_hwnd, DSO_WM_ASYNCH_STATECHANGE, DSO_STATE_RETURNFROMMODAL, (LPARAM)TRUE);
}
}
////////////////////////////////////////////////////////////////////////
// CDsoFramerControl::UpdateInteractiveState
//
// Called when interactivity changes (mostly due to print preview).
//
STDMETHODIMP_(void) CDsoFramerControl::UpdateInteractiveState(BOOL fActive)
{
if (fActive)
{
m_fNoInteractive = FALSE;
if (m_fShowMenuPrev) put_Menubar(VARIANT_TRUE);
if (!m_fShowToolsPrev) put_Toolbars(VARIANT_FALSE);
// Notify control host that preview mode has ended...
RaiseAutomationEvent(DSOF_DISPID_ENDPREVIEW, 0, NULL);
}
else
{
m_fShowMenuPrev = m_fShowMenuBar;
m_fShowToolsPrev = m_fShowToolbars;
if (m_fShowMenuBar) put_Menubar(VARIANT_FALSE);
if (!m_fShowToolbars) put_Toolbars(VARIANT_TRUE);
m_fNoInteractive = TRUE;
}
return;
}
////////////////////////////////////////////////////////////////////////
// CDsoFramerControl::OnPaletteChanged
//
// This method is also called from the subclassed parent. Per docobject
// spec, a ui active object should get first chance of any palette updates.
//
STDMETHODIMP_(void) CDsoFramerControl::OnPaletteChanged(HWND hwndPalChg)
{
ODS("CDsoFramerControl::OnPaletteChanged\n");
if (m_pDocObjFrame) m_pDocObjFrame->OnNotifyPaletteChanged(hwndPalChg);
}
////////////////////////////////////////////////////////////////////////
// CDsoFramerControl::OnSysCommandMenu
//
// Checks for menu shortcut keys when ui active.
//
STDMETHODIMP_(BOOL) CDsoFramerControl::OnSysCommandMenu(CHAR ch)
{
if (m_fUIActive)
{
TRACE1("CDsoFramerControl::OnSysCommandMenu(%d)\n", (DWORD)ch);
return TRUE;
}
return FALSE;
}
////////////////////////////////////////////////////////////////////////
// CDsoFramerControl::GetActivePopupMenu
//
// Constructs our popup menu and returns the handle. The menu can be
// either the File menu by itself (no docobj is open) or the merged
// menu as a popup.
//
STDMETHODIMP_(HMENU) CDsoFramerControl::GetActivePopupMenu()
{
HMENU hPopup, hMergedMenu, hServerMenu;
// If we haven't made a File menu yet, make it. Here is where you might
// want to add custom items if you have other file-level commands you would
// the control to support. These are the basics...
if (!m_hmenuFilePopup)
{
m_hmenuFilePopup = CreatePopupMenu(); m_cMenuItems = 0;
if (!m_hmenuFilePopup) return NULL;
AppendMenu(m_hmenuFilePopup, MF_STRING, MNU_NEW, "新建&...\tCtrl+N");
AppendMenu(m_hmenuFilePopup, MF_STRING, MNU_OPEN, "打开&...\tCtrl+O");
AppendMenu(m_hmenuFilePopup, MF_STRING, MNU_CLOSE, "关闭&");
AppendMenu(m_hmenuFilePopup, MF_SEPARATOR, 0, NULL);
AppendMenu(m_hmenuFilePopup, MF_STRING, MNU_SAVE, "保存&\tCtrl+S");
AppendMenu(m_hmenuFilePopup, MF_STRING, MNU_SAVEAS, "另存为&...");
AppendMenu(m_hmenuFilePopup, MF_SEPARATOR, 0, NULL);
AppendMenu(m_hmenuFilePopup, MF_STRING, MNU_PGSETUP, "&页面设置...");
AppendMenu(m_hmenuFilePopup, MF_STRING, MNU_PRINTPV, "&页面浏览");
AppendMenu(m_hmenuFilePopup, MF_STRING, MNU_PRINT, "&打印...");
AppendMenu(m_hmenuFilePopup, MF_SEPARATOR, 0, NULL);
AppendMenu(m_hmenuFilePopup, MF_STRING, MNU_PROPS, "&属性");
}
//Create menu definetools ;dengll 08.07.07
if(!m_hmenuDefinePopup)
{
m_hmenuDefinePopup= CreatePopupMenu(); m_cMenuItems = 12; //Create dengll 08.07.07
if(!m_hmenuDefinePopup) return NULL;
AppendMenu(m_hmenuDefinePopup, MF_STRING, MNU_DeFine, "打开批注");//Create dengll 08.07.07
AppendMenu(m_hmenuDefinePopup, MF_STRING, MNU_DeFine, "关闭批注");//Create dengll 08.07.07
AppendMenu(m_hmenuDefinePopup, MF_SEPARATOR, 0, NULL);//Create dengll 08.07.07
AppendMenu(m_hmenuDefinePopup, MF_STRING, MNU_DeFine, "添加Note");//Create dengll 08.07.07
AppendMenu(m_hmenuDefinePopup, MF_STRING, MNU_DeFine, "删除Note");//Create dengll 08.07.07
}
// If we have a docobj and it has a merged menu, then lets return a
// merged menu between the docobj and our file menu...
if ((m_pDocObjFrame) && (m_pDocObjFrame->GetMenuHWND()))
{
// We only need to create the merged copy once.
if (!(hMergedMenu = m_pDocObjFrame->GetMergedMenu()))
{
hMergedMenu = CreatePopupMenu(); m_cMenuItems = 0;
if ((hMergedMenu) && (hServerMenu = (m_pDocObjFrame->GetActiveMenu())))
{
CHAR szbuf[MAX_PATH];
HMENU hT;
CHAR *pch;
InsertMenu(hMergedMenu, 0, MF_BYPOSITION|MF_POPUP, (UINT)m_hmenuFilePopup, "文件&");
InsertMenu(hMergedMenu, 12, MF_BYPOSITION|MF_POPUP, (UINT)m_hmenuDefinePopup, "自定义菜单(&D)");
m_rgchMenuAccel[0] = 'f';
int cbMenuCnt = GetMenuItemCount(hServerMenu);
if (cbMenuCnt > DSO_MAX_MENUITEMS) cbMenuCnt = DSO_MAX_MENUITEMS;
for (int i = 0; i < cbMenuCnt; i++)
{
hT = GetSubMenu(hServerMenu, i);
if (hT)
{
szbuf[0] = '\0';
GetMenuString(hServerMenu, i, szbuf, MAX_PATH, MF_BYPOSITION);
InsertMenu(hMergedMenu, (i + 1), MF_BYPOSITION|MF_POPUP, (UINT)hT, szbuf);
pch = szbuf;
while (*pch && (*pch++ != '&'))
;
m_rgchMenuAccel[i + 1] = (CHAR)((*pch) ? ASCII_LOWERCASE(*pch) : 0xFF);
}
}
if (cbMenuCnt < DSO_MAX_MENUITEMS)
m_rgchMenuAccel[cbMenuCnt + 1] = 0x00;
m_pDocObjFrame->SetMergedMenu(hMergedMenu);
}
}
hPopup = hMergedMenu;
}
else
{
hPopup = m_hmenuFilePopup;
m_rgchMenuAccel[0] = 'f';
m_rgchMenuAccel[1] = 0;
}
return hPopup;
}
////////////////////////////////////////////////////////////////////////
// CDsoFramerControl::FRunningInDesignMode
//
// Determines if we are in design mode. Called when painting the control
// and when deciding whether to subclass the parent.
//
STDMETHODIMP_(BOOL) CDsoFramerControl::FRunningInDesignMode()
{
IDispatch *pdisp;
// We must have a control site.
CHECK_NULL_RETURN(m_pClientSite, FALSE);
// If we have done this before, we don't need to keep doing it unless
// the host has notified us of the state change (see our code in
// XOleControl::OnAmbientPropertyChange)...
if ((!m_fModeFlagValid) &&
SUCCEEDED(m_pClientSite->QueryInterface(IID_IDispatch, (void **)&pdisp)))
{
VARIANT vtUserMode;
m_fDesignMode = FALSE; // assume run mode
if (SUCCEEDED(DsoDispatchInvoke(pdisp, NULL,
DISPID_AMBIENT_USERMODE, DISPATCH_PROPERTYGET, 0, NULL, &vtUserMode)))
{
// UserMode is True when control is in Run mode, False when in design.
// We assume run mode, so we only care to set the flag if in design.
m_fDesignMode = !(BOOL_FROM_VARIANT(vtUserMode, TRUE));
VariantClear(&vtUserMode);
}
m_fModeFlagValid = TRUE;
// Release the IDispatch pointer...
pdisp->Release();
}
return m_fDesignMode;
}
////////////////////////////////////////////////////////////////////////
// CDsoFramerControl::InvalidateAllChildWindows
//
// Invalidate all child windows attached to the window passed.
//
STDMETHODIMP_(BOOL) CDsoFramerControl::InvalidateAllChildWindows(HWND hwnd)
{
ODS("CDsoFramerControl::InvalidateAllChildWindows()\n");
return EnumChildWindows(hwnd, InvalidateAllChildWindowsCallback, 0);
}
STDMETHODIMP_(BOOL) CDsoFramerControl::InvalidateAllChildWindowsCallback(HWND hwnd, LPARAM lParam)
{
RECT rc;
GetClientRect(hwnd, &rc);
InvalidateRect(hwnd, &rc, TRUE);
return TRUE;
}
////////////////////////////////////////////////////////////////////////
// CDsoFramerControl::RaiseAutomationEvent
//
// Raises automation events to host application.
//
STDMETHODIMP CDsoFramerControl::RaiseAutomationEvent(DISPID did, ULONG cargs, VARIANT *pvtargs)
{
HRESULT hr = ((m_fModalState) ? DISP_E_EXCEPTION : S_FALSE);
TRACE1("CDsoFramerControl::RaiseAutomationEvent(%d)\n", did);
// We should only raise event if we have sink, not already in a event, and
// we are not in modal condition with respect to the remote server...
if ((m_dispEvents) && (!m_fFreezeEvents) && (!m_fModalState))
{
m_fFreezeEvents = TRUE;
hr = DsoDispatchInvoke(m_dispEvents, NULL, did, 0, cargs, pvtargs, NULL);
m_fFreezeEvents = FALSE;
}
return hr;
}
////////////////////////////////////////////////////////////////////////
//
// CDsoFramerControl::DoDialogAction
//
// A very simple implementation of a New/Open/Save dialogs to serve as
// default actions in case developer does not override these "File"
// commands in OnFileCommand.
//
STDMETHODIMP CDsoFramerControl::DoDialogAction(dsoShowDialogType item)
{
HRESULT hr = S_FALSE;
BSTR bstr;
BOOL fReadOnly;
VARIANT vT[3];
static const WCHAR v_wszFileFilter[] =
L"Microsoft Office Files\0*.doc;*.docx;*.docm;*.rtf;*.xls;*.xlsx;*.xlsm;*.csv;*.ppt;*.pptx;*.pptm;*.mpp;*.vsd;*.vdx\0"
L"Microsoft Word Files\0*.doc;*.docx;*.docm;*.rtf\0"
L"Microsoft Excel Files\0*.xls;*.xlsx;*.xlsm;*.csv\0"
L"Microsoft PowerPoint Files\0*.ppt;*.pptx;*.pptm\0"
L"Microsoft Project Files\0*.mpp\0"
L"Microsoft Visio Files\0*.vsd;*.vdx\0"
L"All Files (*.*)\0*.*\0\0";
// Switch on the action type...
switch (item)
{
case dsoDialogOpen: // Get file from user and call Open...
if (SUCCEEDED(DsoGetFileFromUser(m_hwnd, NULL, (OFN_FILEMUSTEXIST|OFN_EXPLORER),
v_wszFileFilter, 1, NULL, NULL, FALSE, &bstr, &fReadOnly)))
{
vT[0].vt = VT_BSTR; vT[0].bstrVal = bstr;
vT[1].vt = VT_BOOL; vT[1].boolVal = (fReadOnly ? VARIANT_TRUE : VARIANT_FALSE);
vT[2].vt = VT_ERROR; vT[2].scode = DISP_E_PARAMNOTFOUND;
hr = Open(vT[0], vT[1], vT[2], vT[2], vT[2]);
SysFreeString(bstr);
}
break;
case dsoDialogSave: // Get file from user and call Save...
{
LPWSTR pwszSaveType = NULL;
LPWSTR pwszDefExt = NULL;
if (m_pDocObjFrame)
m_pDocObjFrame->GetDocumentTypeAndFileExtension(&pwszSaveType, &pwszDefExt);
if (SUCCEEDED(DsoGetFileFromUser(m_hwnd, NULL, (OFN_HIDEREADONLY|OFN_OVERWRITEPROMPT|OFN_EXPLORER),
((pwszSaveType) ? pwszSaveType : v_wszFileFilter), 1, pwszDefExt, NULL, TRUE, &bstr, NULL)))
{
vT[0].vt = VT_BSTR; vT[0].bstrVal = bstr;
vT[1].vt = VT_BOOL; vT[1].boolVal = VARIANT_TRUE;
vT[2].vt = VT_ERROR; vT[2].scode = DISP_E_PARAMNOTFOUND;
hr = Save(vT[0], vT[1], vT[2], vT[2]);
SysFreeString(bstr);
}
if (pwszSaveType) DsoMemFree(pwszSaveType);
if (pwszDefExt) DsoMemFree(pwszDefExt);
}
break;
case dsoDialogNew: // Get either ProgID or File to create new object from...
if (SUCCEEDED(DsoGetOleInsertObjectFromUser(m_hwnd, L"Insert New Document Object",
(IOF_SELECTCREATENEW | IOF_DISABLELINK | IOF_DISABLEDISPLAYASICON | IOF_HIDECHANGEICON),
TRUE, FALSE, &bstr, NULL)))
{
hr = CreateNew(bstr);
SysFreeString(bstr);
}
break;
default: MessageBeep(0);
}
return hr;
}
////////////////////////////////////////////////////////////////////////
// CDsoFramerControl::SetTempServerLock
//
// Sets up lock of OLE server to make unload and new load of files faster
// and to avoid race conditions on reload of file.
//
STDMETHODIMP CDsoFramerControl::SetTempServerLock(BOOL fLock)
{
HRESULT hr = S_FALSE;
TRACE1("CDsoFramerControl::SetTempServerLock(%d)\n", fLock);
if (fLock)
{
CLSID *pclsid;
// First get the the CLSID of the current loaded object...
pclsid = m_pDocObjFrame->GetServerCLSID();
// If we already have a lock, determine if user is asking us to lock
// the same server (we only lock once for a given server type)...
if (m_pServerLock)
{
if (*(m_pServerLock->GetServerCLSID()) == *pclsid)
return S_FALSE;
// If the current document is from a different server, free the old lock...
hr = SetTempServerLock(FALSE);
ASSERT(SUCCEEDED(hr)); // Sanity check in debug...
}
// To lock the server, just make a dummy OLE object and don't ever site it...
m_pServerLock = CDsoDocObject::CreateInstance((IDsoDocObjectSite*)&m_xDsoDocObjectSite);
hr = ((m_pServerLock) ? m_pServerLock->CreateDocObject(*pclsid) : E_OUTOFMEMORY);
if (SUCCEEDED(hr))
{
hr = m_pServerLock->SetRunningServerLock(TRUE);
// If we lock Excel, it steals focus from this host to the lock object, so we
// need to take it back so the real object isn't mixed up state...
if (SUCCEEDED(hr) && (m_pServerLock->IsExcelObject()) && (m_fAppActive))
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -