Annotation of mstools/ole20/samples/outline/svrinpl.c, revision 1.1

1.1     ! root        1: /*************************************************************************
        !             2: ** 
        !             3: **    OLE 2 Server Sample Code
        !             4: **    
        !             5: **    svrinpl.c
        !             6: **    
        !             7: **    This file contains all interfaces, methods and related support
        !             8: **    functions for an In-Place Object (Server) application (aka. Visual
        !             9: **    Editing). The in-place Object application includes the following
        !            10: **    implementation objects: 
        !            11: **    
        !            12: **    ServerDoc Object
        !            13: **      exposed interfaces:
        !            14: **          IOleInPlaceObject
        !            15: **          IOleInPlaceActiveObject
        !            16: **    
        !            17: **    ServerApp Object
        !            18: **      exposed interfaces:
        !            19: **          IUnknown
        !            20: **    
        !            21: **    (c) Copyright Microsoft Corp. 1992 - 1993 All Rights Reserved
        !            22: **
        !            23: *************************************************************************/
        !            24: 
        !            25: 
        !            26: #include "outline.h"
        !            27: 
        !            28: OLEDBGDATA
        !            29: 
        !            30: extern LPOUTLINEAPP             g_lpApp;
        !            31: 
        !            32: 
        !            33: #if defined( INPLACE_SVR )
        !            34: 
        !            35: /* OLE2NOTE: the object should compose a string that is used by
        !            36: **    in-place containers to be used for the window titles. this string
        !            37: **    is passed to the container application via
        !            38: **    IOleInPlaceUIWindow::SetActiveObject. the string should have the
        !            39: **    following form:
        !            40: **          <application name> - <object short type name>
        !            41: **    SDI containers can use the string directly to display in the
        !            42: **    frame window title. the container would concatenate the string 
        !            43: **    " in <container doc name>".
        !            44: **    an MDI container with the MDI child window maximized can do the
        !            45: **    same as the SDI container. an MDI container with the MDI child
        !            46: **    windows NOT maximized can look for the " - " in the string from
        !            47: **    the object. the first part of the string (app name) would be put
        !            48: **    as the frame window title; the second part would be composed with
        !            49: **    " in <container doc name>" and used as the MDI child window
        !            50: **    title. 
        !            51: */
        !            52: 
        !            53: // REVIEW: should use string resource for messages
        !            54: char g_szIPObjectTitle[] = APPNAME " - " SHORTUSERTYPENAME;
        !            55: 
        !            56: extern RECT g_rectNull;
        !            57: 
        !            58: 
        !            59: 
        !            60: /*************************************************************************
        !            61: ** ServerDoc::IOleInPlaceObject interface implementation
        !            62: *************************************************************************/
        !            63: 
        !            64: // IOleInPlaceObject::QueryInterface method
        !            65: 
        !            66: STDMETHODIMP SvrDoc_IPObj_QueryInterface(
        !            67:         LPOLEINPLACEOBJECT  lpThis,
        !            68:         REFIID              riid,
        !            69:         LPVOID FAR *        lplpvObj
        !            70: )
        !            71: {
        !            72:     LPSERVERDOC lpServerDoc =
        !            73:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !            74: 
        !            75:     return OleDoc_QueryInterface((LPOLEDOC)lpServerDoc, riid, lplpvObj);
        !            76: }
        !            77: 
        !            78: 
        !            79: // IOleInPlaceObject::AddRef method
        !            80: 
        !            81: STDMETHODIMP_(ULONG) SvrDoc_IPObj_AddRef(LPOLEINPLACEOBJECT lpThis)
        !            82: {
        !            83:     LPSERVERDOC lpServerDoc =
        !            84:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !            85: 
        !            86:     OleDbgAddRefMethod(lpThis, "IOleInPlaceObject");
        !            87: 
        !            88:     return OleDoc_AddRef((LPOLEDOC)lpServerDoc);
        !            89: }
        !            90: 
        !            91: 
        !            92: // IOleInPlaceObject::Release method
        !            93: 
        !            94: STDMETHODIMP_(ULONG) SvrDoc_IPObj_Release(LPOLEINPLACEOBJECT lpThis)
        !            95: {
        !            96:     LPSERVERDOC lpServerDoc =
        !            97:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !            98:     
        !            99:     OleDbgReleaseMethod(lpThis, "IOleInPlaceObject");
        !           100: 
        !           101:     return OleDoc_Release((LPOLEDOC)lpServerDoc);
        !           102: }
        !           103: 
        !           104: 
        !           105: // IOleInPlaceObject::GetWindow method
        !           106: 
        !           107: STDMETHODIMP SvrDoc_IPObj_GetWindow(
        !           108:         LPOLEINPLACEOBJECT  lpThis,
        !           109:         HWND FAR*           lphwnd
        !           110: )
        !           111: {
        !           112:     LPSERVERDOC lpServerDoc =
        !           113:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           114: 
        !           115:     OLEDBG_BEGIN2("SvrDoc_IPObj_GetWindow\r\n")
        !           116: 
        !           117:     *lphwnd = ((LPOUTLINEDOC)lpServerDoc)->m_hWndDoc;
        !           118: 
        !           119:     OLEDBG_END2
        !           120:     return S_OK;
        !           121: }
        !           122: 
        !           123: 
        !           124: // IOleInPlaceObject::ContextSensitiveHelp method
        !           125: 
        !           126: STDMETHODIMP SvrDoc_IPObj_ContextSensitiveHelp(
        !           127:         LPOLEINPLACEOBJECT  lpThis,
        !           128:         BOOL                fEnable
        !           129: )
        !           130: {
        !           131:     LPSERVERDOC lpServerDoc =
        !           132:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           133: 
        !           134:     OLEDBG_BEGIN2("SvrDoc_IPObj_ContextSensitiveHelp\r\n")
        !           135: 
        !           136:     lpServerDoc->m_lpIPData->fInCSHelpMode = fEnable;
        !           137: 
        !           138:     OLEDBG_END2
        !           139:     return S_OK;
        !           140: }
        !           141: 
        !           142: 
        !           143: // IOleInPlaceObject::InPlaceDeactivate method
        !           144: 
        !           145: STDMETHODIMP SvrDoc_IPObj_InPlaceDeactivate(LPOLEINPLACEOBJECT lpThis)
        !           146: {
        !           147:     LPSERVERDOC lpServerDoc =
        !           148:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           149:     HRESULT hrErr;
        !           150: 
        !           151:     OLEDBG_BEGIN2("SvrDoc_IPObj_InPlaceDeactivate\r\n")
        !           152: 
        !           153:     hrErr = ServerDoc_DoInPlaceDeactivate(lpServerDoc);
        !           154: 
        !           155:     OLEDBG_END2
        !           156:     return hrErr;
        !           157: }
        !           158: 
        !           159: 
        !           160: // IOleInPlaceObject::UIDeactivate method
        !           161: 
        !           162: STDMETHODIMP SvrDoc_IPObj_UIDeactivate(LPOLEINPLACEOBJECT lpThis)
        !           163: {
        !           164:     LPSERVERDOC     lpServerDoc =
        !           165:                         ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           166:     LPSERVERAPP     lpServerApp = (LPSERVERAPP)g_lpApp;
        !           167:        LPOUTLINEDOC    lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !           168:     LPINPLACEDATA   lpIPData = lpServerDoc->m_lpIPData;
        !           169:     LPLINELIST         lpLL = (LPLINELIST)&((LPOUTLINEDOC)lpServerDoc)->m_LineList;
        !           170:        HWND                    hWndApp = OutlineApp_GetWindow(g_lpApp);
        !           171:     
        !           172:     OLEDBG_BEGIN2("SvrDoc_IPObj_UIDeactivate\r\n");
        !           173: 
        !           174:     if (!lpServerDoc->m_fUIActive) {
        !           175:         OLEDBG_END2
        !           176:         return NOERROR;
        !           177:     }
        !           178: 
        !           179:     lpServerDoc->m_fUIActive = FALSE;
        !           180: 
        !           181:        // Clip the hatch window to the size of pos rect so, that the object 
        !           182:        // adornments and hatch border will not be visible.
        !           183:     ServerDoc_ResizeInPlaceWindow(lpServerDoc,
        !           184:             (LPRECT)&(lpServerDoc->m_lpIPData->rcPosRect),
        !           185:             (LPRECT)&(lpServerDoc->m_lpIPData->rcPosRect)
        !           186:     );
        !           187: 
        !           188:     if (lpIPData->lpDoc) 
        !           189:         lpIPData->lpDoc->lpVtbl->SetActiveObject(lpIPData->lpDoc, NULL, NULL);
        !           190: 
        !           191:     if (lpIPData->lpFrame) { 
        !           192:         lpIPData->lpFrame->lpVtbl->SetActiveObject(
        !           193:             lpIPData->lpFrame,
        !           194:             NULL,
        !           195:             NULL
        !           196:         );
        !           197:     }
        !           198:     
        !           199: #if defined( USE_FRAMETOOLS )
        !           200:        /* OLE2NOTE: we must hide our frame tools here but NOT call
        !           201:        **    IOleInPlaceFrame::SetBorderSpace(NULL) or SetMenu(NULL).
        !           202:        **    we must hide our tools BEFORE calling
        !           203:        **    IOleInPlaceSite::OnUIDeactivate. the container will put
        !           204:        **    his menus and tools back when OnUIDeactivate is called.
        !           205:        */
        !           206:     ServerDoc_RemoveFrameLevelTools(lpServerDoc);
        !           207: #endif
        !           208: 
        !           209:     OLEDBG_BEGIN2("IOleInPlaceSite::OnUIDeactivate called\r\n");
        !           210:     lpIPData->lpSite->lpVtbl->OnUIDeactivate(lpIPData->lpSite, FALSE);
        !           211:     OLEDBG_END2
        !           212: 
        !           213:        /* Reset to use our normal app's accelerator table */
        !           214:     g_lpApp->m_hAccel = g_lpApp->m_hAccelApp;
        !           215:     g_lpApp->m_hWndAccelTarget = hWndApp;
        !           216: 
        !           217:     OLEDBG_END2
        !           218:                
        !           219: #if !defined( SVR_INSIDEOUT )
        !           220:     /* OLE2NOTE: an "outside-in" style in-place server would hide its
        !           221:     **    window here. an "inside-out" style server leaves its window
        !           222:     **    visible when it is UIDeactivated. it would only hide its
        !           223:     **    window when InPlaceDeactivated. this app is an "inside-out" 
        !           224:     **    style server. it is recommended for most server to support
        !           225:     **    inside-out behavior if possible.
        !           226:     */
        !           227:        ServerDoc_DoInPlaceHide(lpServerDoc);
        !           228: #endif // INSIEDOUT
        !           229: 
        !           230:     return NOERROR;
        !           231: }
        !           232: 
        !           233: 
        !           234: // IOleInPlaceObject::SetObjectRects method
        !           235: 
        !           236: STDMETHODIMP SvrDoc_IPObj_SetObjectRects(
        !           237:         LPOLEINPLACEOBJECT  lpThis,
        !           238:         LPCRECT             lprcPosRect,
        !           239:         LPCRECT             lprcClipRect
        !           240: )
        !           241: {
        !           242:     LPSERVERDOC  lpServerDoc =
        !           243:                     ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           244:     LPINPLACEDATA lpIPData = lpServerDoc->m_lpIPData;
        !           245:     LPLINELIST   lpLL = OutlineDoc_GetLineList((LPOUTLINEDOC)lpServerDoc);
        !           246: 
        !           247:     OLEDBG_BEGIN2("SvrDoc_IPObj_SetObjectRects\r\n")
        !           248: 
        !           249:     OleDbgOutRect3("SvrDoc_IPObj_SetObjectRects (PosRect)", 
        !           250:                        (LPRECT)lprcPosRect);
        !           251:     OleDbgOutRect3("SvrDoc_IPObj_SetObjectRects (ClipRect)", 
        !           252:             (LPRECT)lprcClipRect);
        !           253: 
        !           254:        // save the current PosRect and ClipRect
        !           255:        lpIPData->rcPosRect = *lprcPosRect;
        !           256:        lpIPData->rcClipRect = *lprcClipRect;
        !           257: 
        !           258:        if (! lpServerDoc->m_fUIActive) // hatch and adornaments must not be drawn
        !           259:                lprcClipRect = lprcPosRect;
        !           260:        
        !           261:        ServerDoc_ResizeInPlaceWindow(
        !           262:                        lpServerDoc, (LPRECT)lprcPosRect, (LPRECT)lprcClipRect);
        !           263:     
        !           264: 
        !           265:     /* reset the horizontal extent of the listbox. this makes 
        !           266:     **    the listbox realize that a scroll bar is not needed.
        !           267:     */
        !           268:     SendMessage(
        !           269:             lpLL->m_hWndListBox, 
        !           270:             LB_SETHORIZONTALEXTENT, 
        !           271:             (int) 0,
        !           272:             0L
        !           273:     );
        !           274:     SendMessage(
        !           275:             lpLL->m_hWndListBox,
        !           276:             LB_SETHORIZONTALEXTENT,
        !           277:             (int) (lpIPData->rcPosRect.right - lpIPData->rcPosRect.left),
        !           278:             0L
        !           279:     );
        !           280: 
        !           281:     OLEDBG_END2
        !           282:     return NOERROR;
        !           283: }
        !           284: 
        !           285: 
        !           286: // IOleInPlaceObject::ReactivateAndUndo method
        !           287: 
        !           288: STDMETHODIMP SvrDoc_IPObj_ReactivateAndUndo(LPOLEINPLACEOBJECT lpThis)
        !           289: {
        !           290:     OLEDBG_BEGIN2("SvrDoc_IPObj_ReactivateAndUndo\r\n")
        !           291: 
        !           292:     // We do not support support UNDO.
        !           293: 
        !           294:     /* REVIEW: for debugging purposes it would be useful to give a
        !           295:     **    message box indicating that this method has been called.
        !           296:     */
        !           297: 
        !           298:     OLEDBG_END2
        !           299:     return NOERROR;
        !           300: }
        !           301: 
        !           302: 
        !           303: /*************************************************************************
        !           304: ** ServerDoc::IOleInPlaceActiveObject interface implementation
        !           305: *************************************************************************/
        !           306: 
        !           307: // IOleInPlaceActiveObject::QueryInterface method
        !           308: 
        !           309: STDMETHODIMP SvrDoc_IPActiveObj_QueryInterface(
        !           310:         LPOLEINPLACEACTIVEOBJECT    lpThis,
        !           311:         REFIID                      riid,
        !           312:         LPVOID FAR *                lplpvObj
        !           313: )
        !           314: {
        !           315:     SCODE sc = E_NOINTERFACE;
        !           316:     LPSERVERDOC lpServerDoc =
        !           317:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           318: 
        !           319:     /* The container should not be able to access the other interfaces
        !           320:     ** of our object by doing QI on this interface. 
        !           321:     */
        !           322: 
        !           323:     *lplpvObj = NULL;
        !           324:     if (IsEqualIID(riid, &IID_IUnknown) ||
        !           325:         IsEqualIID(riid, &IID_IOleWindow) ||
        !           326:         IsEqualIID(riid, &IID_IOleInPlaceActiveObject)) {
        !           327:         OleDbgOut4("OleDoc_QueryInterface: IOleInPlaceActiveObject* RETURNED\r\n");
        !           328: 
        !           329:         *lplpvObj = lpThis;
        !           330:         OleDoc_AddRef((LPOLEDOC)lpServerDoc);
        !           331:         sc = NOERROR;
        !           332:     }
        !           333:     
        !           334:     OleDbgQueryInterfaceMethod(*lplpvObj);
        !           335: 
        !           336:     return ResultFromScode(sc);   
        !           337: }
        !           338: 
        !           339: 
        !           340: // IOleInPlaceActiveObject::AddRef method
        !           341: 
        !           342: STDMETHODIMP_(ULONG) SvrDoc_IPActiveObj_AddRef(
        !           343:         LPOLEINPLACEACTIVEOBJECT lpThis
        !           344: )
        !           345: {
        !           346:     LPSERVERDOC lpServerDoc =
        !           347:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           348: 
        !           349:     OleDbgAddRefMethod(lpThis, "IOleInPlaceActiveObject");
        !           350: 
        !           351:     return OleDoc_AddRef((LPOLEDOC)lpServerDoc);
        !           352: }
        !           353: 
        !           354: 
        !           355: // IOleInPlaceActiveObject::Release method
        !           356: 
        !           357: STDMETHODIMP_(ULONG) SvrDoc_IPActiveObj_Release(
        !           358:         LPOLEINPLACEACTIVEOBJECT lpThis
        !           359: )
        !           360: {
        !           361:     LPSERVERDOC lpServerDoc =
        !           362:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           363:     
        !           364:     OleDbgReleaseMethod(lpThis, "IOleInPlaceActiveObject");
        !           365: 
        !           366:     return OleDoc_Release((LPOLEDOC)lpServerDoc);
        !           367: }
        !           368: 
        !           369: 
        !           370: // IOleInPlaceActiveObject::GetWindow method
        !           371: 
        !           372: STDMETHODIMP SvrDoc_IPActiveObj_GetWindow(
        !           373:         LPOLEINPLACEACTIVEOBJECT    lpThis,
        !           374:         HWND FAR*                   lphwnd
        !           375: )
        !           376: {
        !           377:     LPSERVERDOC lpServerDoc =
        !           378:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           379: 
        !           380:     OLEDBG_BEGIN2("SvrDoc_IPActiveObj_GetWindow\r\n")
        !           381: 
        !           382:     *lphwnd = ((LPOUTLINEDOC)lpServerDoc)->m_hWndDoc;
        !           383: 
        !           384:     OLEDBG_END2
        !           385:     return NOERROR;
        !           386: }
        !           387: 
        !           388: 
        !           389: // IOleInPlaceActiveObject::ContextSensitiveHelp method
        !           390: 
        !           391: STDMETHODIMP SvrDoc_IPActiveObj_ContextSensitiveHelp(
        !           392:         LPOLEINPLACEACTIVEOBJECT    lpThis,
        !           393:         BOOL                        fEnable
        !           394: )
        !           395: {
        !           396:     LPSERVERDOC lpServerDoc =
        !           397:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           398: 
        !           399:     OLEDBG_BEGIN2("SvrDoc_IPActiveObj_ContextSensitiveHelp\r\n")
        !           400: 
        !           401:     lpServerDoc->m_lpIPData->fInCSHelpMode = fEnable;
        !           402: 
        !           403:     OLEDBG_END2
        !           404:     return NOERROR;
        !           405: }
        !           406: 
        !           407: 
        !           408: // IOleInPlaceActiveObject::TranslateAccelerator method
        !           409: 
        !           410: STDMETHODIMP SvrDoc_IPActiveObj_TranslateAccelerator(
        !           411:         LPOLEINPLACEACTIVEOBJECT    lpThis,
        !           412:         LPMSG                       lpmsg
        !           413: )
        !           414: {
        !           415:     // This will never be called because this server is implemented as an EXE
        !           416:     return NOERROR; 
        !           417: }
        !           418: 
        !           419: 
        !           420: // IOleInPlaceActiveObject::OnFrameWindowActivate method
        !           421: 
        !           422: STDMETHODIMP SvrDoc_IPActiveObj_OnFrameWindowActivate(
        !           423:         LPOLEINPLACEACTIVEOBJECT    lpThis,
        !           424:         BOOL                        fActivate
        !           425: )
        !           426: {
        !           427:     LPOUTLINEDOC lpOutlineDoc = (LPOUTLINEDOC)
        !           428:             ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           429:     HWND hWndDoc = OutlineDoc_GetWindow(lpOutlineDoc);
        !           430: 
        !           431:     OleDbgOut2("SvrDoc_IPActiveObj_OnFrameWindowActivate\r\n");
        !           432: 
        !           433:        /* OLE2NOTE: this is a notification of the container application's
        !           434:        **    WM_ACTIVATEAPP status. some applications may find this
        !           435:        **    important. we need to update the enable/disable status of our
        !           436:     **    tool bar buttons.
        !           437:        */
        !           438: 
        !           439:     // OLE2NOTE: We can't call OutlineDoc_UpdateFrameToolButtons
        !           440:     //           right away which 
        !           441:     //           would generate some OLE calls and eventually 
        !           442:     //           WM_ACTIVATEAPP and a loop was formed. Therefore, we
        !           443:     //           should delay the frame tool initialization until 
        !           444:     //                  WM_ACTIVATEAPP is finished by posting a message
        !           445:     //                  to ourselves.
        !           446: 
        !           447:     /* Update enable/disable state of buttons in toolbar */
        !           448:     if (fActivate) 
        !           449:         PostMessage(hWndDoc, WM_U_INITFRAMETOOLS, 0, 0L);
        !           450: 
        !           451:     return NOERROR;
        !           452: }
        !           453: 
        !           454: 
        !           455: // IOleInPlaceActiveObject::OnDocWindowActivate method
        !           456: 
        !           457: STDMETHODIMP SvrDoc_IPActiveObj_OnDocWindowActivate(
        !           458:         LPOLEINPLACEACTIVEOBJECT    lpThis,
        !           459:         BOOL                        fActivate
        !           460: )
        !           461: {
        !           462:     LPSERVERDOC     lpServerDoc =
        !           463:                         ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           464:     LPINPLACEDATA   lpIPData = lpServerDoc->m_lpIPData;
        !           465: 
        !           466:     OLEDBG_BEGIN2("SvrDoc_IPActiveObj_OnDocWindowActivate\r\n")
        !           467: 
        !           468:     if (fActivate) {
        !           469:         ServerDoc_AddFrameLevelUI(lpServerDoc);
        !           470:     }
        !           471:     else {
        !           472: #if defined( USE_FRAMETOOLS )
        !           473:                /* OLE2NOTE: we must NOT call IOleInPlaceFrame::SetBorderSpace(NULL)
        !           474:                **    or SetMenu(NULL) here. we should simply hide our tools.
        !           475:                */
        !           476:         ServerDoc_RemoveFrameLevelTools(lpServerDoc);
        !           477: #endif  
        !           478:     }
        !           479: 
        !           480:     OLEDBG_END2
        !           481:     return NOERROR;
        !           482: }
        !           483: 
        !           484: 
        !           485: // IOleInPlaceActiveObject::ResizeBorder method
        !           486: 
        !           487: STDMETHODIMP SvrDoc_IPActiveObj_ResizeBorder(
        !           488:         LPOLEINPLACEACTIVEOBJECT    lpThis,
        !           489:         LPCRECT                     lprectBorder,
        !           490:         LPOLEINPLACEUIWINDOW        lpIPUiWnd,
        !           491:                BOOL                                            fFrameWindow
        !           492: )
        !           493: {
        !           494:     LPSERVERDOC lpServerDoc =
        !           495:                     ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           496:        LPOUTLINEDOC lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !           497: 
        !           498:     OLEDBG_BEGIN2("SvrDoc_IPActiveObj_ResizeBorder\r\n")
        !           499: 
        !           500: 
        !           501: #if defined( USE_FRAMETOOLS )
        !           502: 
        !           503:        if (fFrameWindow) {
        !           504:                FrameTools_NegotiateForSpaceAndShow(
        !           505:                                lpOutlineDoc->m_lpFrameTools, 
        !           506:                                (LPRECT)lprectBorder,
        !           507:                                (LPOLEINPLACEFRAME)lpIPUiWnd
        !           508:                );              
        !           509:        }
        !           510: 
        !           511: #endif
        !           512: 
        !           513:     OLEDBG_END2
        !           514:     return NOERROR;
        !           515: }   
        !           516: 
        !           517: 
        !           518: // IOleInPlaceActiveObject::EnableModeless method
        !           519: 
        !           520: STDMETHODIMP SvrDoc_IPActiveObj_EnableModeless(
        !           521:         LPOLEINPLACEACTIVEOBJECT    lpThis,
        !           522:         BOOL                        fEnable
        !           523: )
        !           524: {
        !           525:     LPSERVERDOC lpServerDoc =
        !           526:                     ((struct CDocOleObjectImpl FAR*)lpThis)->lpServerDoc;
        !           527: 
        !           528:     OleDbgOut2("SvrDoc_IPActiveObj_EnableModeless\r\n");
        !           529: 
        !           530:     return NOERROR;
        !           531: }
        !           532: 
        !           533: 
        !           534: /*************************************************************************
        !           535: ** Support Functions
        !           536: *************************************************************************/
        !           537: 
        !           538: 
        !           539: HRESULT ServerDoc_DoInPlaceActivate(
        !           540:         LPSERVERDOC     lpServerDoc,
        !           541:                LONG                    lVerb,
        !           542:         LPMSG           lpmsg, 
        !           543:         LPOLECLIENTSITE lpActiveSite
        !           544: )
        !           545: {
        !           546:     LPOUTLINEAPP                       lpOutlineApp = (LPOUTLINEAPP)g_lpApp;
        !           547:     LPSERVERAPP                                lpServerApp = (LPSERVERAPP)g_lpApp;
        !           548:     LPOLEAPP                lpOleApp = (LPOLEAPP)g_lpApp;
        !           549:     SCODE                   sc = E_FAIL;
        !           550:     RECT                    rcPos;
        !           551:     RECT                    rcClip;
        !           552:     LPINPLACEDATA           lpIPData = lpServerDoc->m_lpIPData;
        !           553:     LPOUTLINEDOC            lpOutlineDoc=(LPOUTLINEDOC)lpServerDoc;
        !           554:     HWND                    hWndDoc = lpOutlineDoc->m_hWndDoc;
        !           555:        HWND                                    hWndHatch = lpServerDoc->m_hWndHatch;
        !           556:     HRESULT                 hrErr;
        !           557:     LPLINELIST              lpLL=(LPLINELIST)&lpOutlineDoc->m_LineList;
        !           558:     LPOLEINPLACESITE    lpIPSite = NULL;
        !           559: 
        !           560:     /* OLE2NOTE: lpActiveSite should be used only for InPlace PLAYing.
        !           561:     **    This app does not do inplace PLAYing, so it never uses
        !           562:     **    lpActiveSite.
        !           563:     */
        !           564: 
        !           565:     /* InPlace activation can only be done if the ClientSite is non-NULL. */
        !           566:     if (! lpServerDoc->m_lpOleClientSite) 
        !           567:         return NOERROR;
        !           568: 
        !           569:     if (! lpServerDoc->m_fInPlaceActive) {
        !           570: 
        !           571:                // if the object is in open mode then we do not want to do inplace
        !           572:                // activation. 
        !           573:                if (IsWindowVisible(lpOutlineDoc->m_hWndDoc))
        !           574:                        return NOERROR;
        !           575:                
        !           576:         lpIPSite = (LPOLEINPLACESITE)OleStdQueryInterface(
        !           577:                 (LPUNKNOWN)lpServerDoc->m_lpOleClientSite,
        !           578:                 &IID_IOleInPlaceSite
        !           579:         );
        !           580:             
        !           581:         if (! lpIPSite)
        !           582:             goto errActivate;
        !           583: 
        !           584:         if (lpIPSite->lpVtbl->CanInPlaceActivate(lpIPSite) != NOERROR)
        !           585:             goto errActivate;
        !           586:     
        !           587:         lpServerDoc->m_fInPlaceActive = TRUE;
        !           588:         if (lpIPSite->lpVtbl->OnInPlaceActivate(lpIPSite) != NOERROR)
        !           589:             goto errActivate;
        !           590: 
        !           591:         if (! ServerDoc_AllocInPlaceData(lpServerDoc)) {
        !           592:             sc = E_OUTOFMEMORY;
        !           593:             lpIPSite->lpVtbl->OnInPlaceDeactivate(lpIPSite);
        !           594:             goto errActivate;
        !           595:         }           
        !           596: 
        !           597:         (lpIPData = lpServerDoc->m_lpIPData)->lpSite = lpIPSite;
        !           598:                goto InPlaceActive;
        !           599: 
        !           600:     errActivate:
        !           601:         lpServerDoc->m_fInPlaceActive = FALSE;
        !           602:         if (lpIPSite) 
        !           603:                        OleStdRelease((LPUNKNOWN)lpIPSite);   
        !           604:         return ResultFromScode(sc);
        !           605:     }       
        !           606: 
        !           607:     
        !           608: InPlaceActive:  
        !           609:                        
        !           610:        if (! lpServerDoc->m_fInPlaceVisible) {
        !           611:                lpServerDoc->m_fInPlaceVisible = TRUE;
        !           612: 
        !           613:                OLEDBG_BEGIN2("IOleInPlaceSite::GetWindow called\r\n");
        !           614:                hrErr = lpIPData->lpSite->lpVtbl->GetWindow(
        !           615:                                        lpIPData->lpSite, 
        !           616:                                        &lpServerDoc->m_hWndParent
        !           617:                );
        !           618:                OLEDBG_END2
        !           619:                if (hrErr != NOERROR) {
        !           620:                        sc = GetScode(hrErr);
        !           621:                        goto errRtn;
        !           622:                }
        !           623:     
        !           624:                if (! lpServerDoc->m_hWndParent)
        !           625:                        goto errRtn;
        !           626:        
        !           627:                /* OLE2NOTE: The server should fill in the "cb" field so that the
        !           628:                **    container can tell what size structure the server is
        !           629:                **    expecting. this enables this structure to be easily extended
        !           630:                **    in future releases of OLE. the container should check this
        !           631:                **    field so that it doesn't try to use fields that do not exist
        !           632:                **    since the server may be using an old structure definition. 
        !           633:                */
        !           634:                _fmemset(
        !           635:                        (LPOLEINPLACEFRAMEINFO)&lpIPData->frameInfo,
        !           636:                        0,
        !           637:                        sizeof(OLEINPLACEFRAMEINFO)
        !           638:                );
        !           639:                lpIPData->frameInfo.cb = sizeof(OLEINPLACEFRAMEINFO);
        !           640: 
        !           641:                OLEDBG_BEGIN2("IOleInPlaceSite::GetWindowContext called\r\n");
        !           642:                hrErr = lpIPData->lpSite->lpVtbl->GetWindowContext(lpIPData->lpSite, 
        !           643:                                        (LPOLEINPLACEFRAME FAR*) &lpIPData->lpFrame,
        !           644:                                        (LPOLEINPLACEUIWINDOW FAR*)&lpIPData->lpDoc,
        !           645:                                        (LPRECT)&rcPos, 
        !           646:                                        (LPRECT)&rcClip, 
        !           647:                                        (LPOLEINPLACEFRAMEINFO)&lpIPData->frameInfo);
        !           648:                OLEDBG_END2
        !           649: 
        !           650:                if (hrErr != NOERROR) {
        !           651:                        sc = GetScode(hrErr);
        !           652:                        goto errRtn;
        !           653:                }
        !           654:                
        !           655:                lpServerApp->m_lpIPData = lpIPData;
        !           656:                ShowWindow(hWndDoc, SW_HIDE);   // make sure we are hidden
        !           657: 
        !           658:                /* OLE2NOTE: reparent in-place server document's window to the
        !           659:                **    special in-place hatch border window. set the in-place site's
        !           660:                **    window as the parent of the hatch window. position the
        !           661:                **    in-place and hatch border windows using the PosRect and
        !           662:                **    ClipRect. 
        !           663:                **    it is important to properly parent and position the in-place
        !           664:                **    server window BEFORE calling IOleInPlaceFrame::SetMenu and
        !           665:                **    SetBorderSpace.
        !           666:                */
        !           667:                ShowWindow(lpServerDoc->m_hWndHatch, SW_SHOW);
        !           668:                // make sure App busy/blocked dialogs are parented to our 
        !           669:                // new hWndFrame
        !           670:                OleStdMsgFilter_SetParentWindow(
        !           671:             lpOleApp->m_lpMsgFilter,lpIPData->frameInfo.hwndFrame);    
        !           672:                SetParent(lpServerDoc->m_hWndHatch, lpServerDoc->m_hWndParent); 
        !           673:                SetParent(hWndDoc, lpServerDoc->m_hWndHatch);   
        !           674: 
        !           675:         OleDbgOutRect3("IOleInPlaceSite::GetWindowContext (PosRect)", 
        !           676:                 (LPRECT)&rcPos);
        !           677:         OleDbgOutRect3("IOleInPlaceSite::GetWindowContext (ClipRect)", 
        !           678:                 (LPRECT)&rcClip);
        !           679: 
        !           680:                // save the current PosRect and ClipRect
        !           681:                lpIPData->rcPosRect  = rcPos;
        !           682:                lpIPData->rcClipRect = rcClip;
        !           683: 
        !           684:                /* OLE2NOTE: build the shared menu for the in-place container and
        !           685:                **    the server. 
        !           686:                */
        !           687:                if (ServerDoc_AssembleMenus (lpServerDoc) != NOERROR)
        !           688:                        goto errRtn;
        !           689: 
        !           690: #if defined( SVR_INSIDEOUT )
        !           691:                if (lVerb == OLEIVERB_INPLACEACTIVATE) {                
        !           692:                        // Clip the hatch window to the size of pos rect so, that 
        !           693:                        // hatch and object adornments  will not be visible.
        !           694:                        ServerDoc_ResizeInPlaceWindow(lpServerDoc,
        !           695:                                (LPRECT)&(lpServerDoc->m_lpIPData->rcPosRect),
        !           696:                                (LPRECT)&(lpServerDoc->m_lpIPData->rcPosRect)
        !           697:                        );
        !           698:                }
        !           699: #endif  // SVR_INSIDEOUT
        !           700:        }
        !           701: 
        !           702: #if defined( SVR_INSIDEOUT )
        !           703:     // OLE2NOTE: if verb is OLEIVERB_INPLACEACTIVATE we do NOT want to 
        !           704:     // show our UI
        !           705:        if (lVerb == OLEIVERB_INPLACEACTIVATE) {
        !           706:         return NOERROR;
        !           707:     }
        !           708: #endif  // SVR_INSIDEOUT
        !           709:        
        !           710:        if (! lpServerDoc->m_fUIActive) {
        !           711:                lpServerDoc->m_fUIActive = TRUE;
        !           712:                OLEDBG_BEGIN2("IOleInPlaceSite::OnUIActivate called\r\n");
        !           713:                hrErr = lpIPData->lpSite->lpVtbl->OnUIActivate(lpIPData->lpSite);
        !           714:                OLEDBG_END2
        !           715:                if (hrErr != NOERROR) {
        !           716:                        lpServerDoc->m_fUIActive = FALSE;
        !           717:                        goto errRtn;
        !           718:                }
        !           719:        
        !           720:                SetFocus(hWndDoc);      
        !           721:                
        !           722:                // Show the object adornments and hacth border around them.
        !           723:                ServerDoc_ResizeInPlaceWindow(lpServerDoc, 
        !           724:                                        (LPRECT)&lpIPData->rcPosRect, 
        !           725:                                        (LPRECT)&lpIPData->rcClipRect
        !           726:                );
        !           727:                
        !           728:                /* OLE2NOTE: IOleInPlaceFrame::SetActiveObject must be called BEFORE
        !           729:                **    IOleInPlaceFrame::SetMenu.
        !           730:                */
        !           731:                lpIPData->lpFrame->lpVtbl->SetActiveObject(
        !           732:                        lpIPData->lpFrame, 
        !           733:                        (LPOLEINPLACEACTIVEOBJECT) &lpServerDoc->m_OleInPlaceActiveObject,
        !           734:                        (LPSTR)g_szIPObjectTitle
        !           735:                );
        !           736:     
        !           737:                if (lpIPData->lpDoc) {
        !           738:                        lpIPData->lpDoc->lpVtbl->SetActiveObject(
        !           739:                                lpIPData->lpDoc, 
        !           740:                                (LPOLEINPLACEACTIVEOBJECT)&lpServerDoc->m_OleInPlaceActiveObject,
        !           741:                                (LPSTR)g_szIPObjectTitle
        !           742:                        );
        !           743:                }
        !           744:     
        !           745:                /* OLE2NOTE: install the menu and frame-level tools on the in-place
        !           746:                **    frame.
        !           747:                */
        !           748:                ServerDoc_AddFrameLevelUI(lpServerDoc);
        !           749:        }
        !           750: 
        !           751:        return NOERROR;
        !           752:                
        !           753: errRtn:     
        !           754:     ServerDoc_DoInPlaceDeactivate(lpServerDoc);
        !           755:     return ResultFromScode(sc);
        !           756: }
        !           757: 
        !           758: 
        !           759: 
        !           760: HRESULT ServerDoc_DoInPlaceDeactivate(LPSERVERDOC lpServerDoc)
        !           761: {
        !           762:     LPINPLACEDATA   lpIPData = lpServerDoc->m_lpIPData;
        !           763:        LPOUTLINEDOC    lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !           764:     
        !           765:     if (!lpServerDoc->m_fInPlaceActive)
        !           766:         return S_OK;
        !           767:         
        !           768:     lpServerDoc->m_fInPlaceActive = FALSE;
        !           769: 
        !           770:     SvrDoc_IPObj_UIDeactivate(
        !           771:             (LPOLEINPLACEOBJECT)&lpServerDoc->m_OleInPlaceObject);
        !           772: 
        !           773: #if defined( SVR_INSIDEOUT )
        !           774:     /* OLE2NOTE: an inside-out style in-place server will
        !           775:     **    NOT hide its window in UIDeactive (an outside-in
        !           776:     **    style object will hide its window in
        !           777:     **    UIDeactivate). thus we need to explicitly hide
        !           778:     **    our window now.
        !           779:     */
        !           780:     ServerDoc_DoInPlaceHide(lpServerDoc);
        !           781: #endif // INSIEDOUT
        !           782: 
        !           783:     OLEDBG_BEGIN2("IOleInPlaceSite::OnInPlaceDeactivate called\r\n");
        !           784:     lpIPData->lpSite->lpVtbl->OnInPlaceDeactivate(lpIPData->lpSite);
        !           785:     OLEDBG_END2
        !           786:                
        !           787:     OleStdRelease((LPUNKNOWN)lpIPData->lpSite);   
        !           788:     lpIPData->lpSite = NULL;
        !           789:     
        !           790:     ServerDoc_FreeInPlaceData(lpServerDoc);
        !           791:        
        !           792:     return NOERROR;
        !           793: }
        !           794: 
        !           795: 
        !           796: HRESULT ServerDoc_DoInPlaceHide(LPSERVERDOC lpServerDoc)
        !           797: {
        !           798:     LPINPLACEDATA   lpIPData = lpServerDoc->m_lpIPData;
        !           799:        LPOUTLINEDOC    lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !           800:     LPOLEAPP        lpOleApp = (LPOLEAPP)g_lpApp;
        !           801:        HWND                    hWndApp = OutlineApp_GetWindow(g_lpApp);
        !           802:        
        !           803:        if (! lpServerDoc->m_fInPlaceVisible)
        !           804:                return NOERROR;
        !           805:        
        !           806:     // Set the parent back to server app's window 
        !           807:        OleDoc_HideWindow((LPOLEDOC)lpServerDoc, FALSE /* fShutdown */);
        !           808: 
        !           809:        lpServerDoc->m_fInPlaceVisible = FALSE;
        !           810: 
        !           811:     lpServerDoc->m_hWndParent = hWndApp;
        !           812:     SetParent(
        !           813:         lpOutlineDoc->m_hWndDoc, 
        !           814:         lpServerDoc->m_hWndParent
        !           815:     );
        !           816: 
        !           817:     // make sure App busy/blocked dialogs are parented to our own hWndApp
        !           818:     OleStdMsgFilter_SetParentWindow(lpOleApp->m_lpMsgFilter, hWndApp);
        !           819:     
        !           820:        // Hide the in-place hatch border window.
        !           821:        ShowWindow(lpServerDoc->m_hWndHatch, SW_HIDE);
        !           822: 
        !           823:     ServerDoc_DisassembleMenus(lpServerDoc);
        !           824:     
        !           825:        /* we no longer need the IOleInPlaceFrame* or the doc's
        !           826:        **    IOleInPlaceWindow* interface pointers.
        !           827:        */
        !           828:     if (lpIPData->lpDoc) {
        !           829:                OleStdRelease((LPUNKNOWN)lpIPData->lpDoc);
        !           830:         lpIPData->lpDoc = NULL;
        !           831:     }       
        !           832: 
        !           833:     if (lpIPData->lpFrame) {
        !           834:         OleStdRelease((LPUNKNOWN)lpIPData->lpFrame);
        !           835:         lpIPData->lpFrame = NULL;
        !           836:     }
        !           837:        
        !           838:     ((LPSERVERAPP)g_lpApp)->m_lpIPData = NULL;
        !           839:        
        !           840:        return NOERROR;
        !           841: }
        !           842: 
        !           843: 
        !           844: BOOL ServerDoc_AllocInPlaceData(LPSERVERDOC lpServerDoc)
        !           845: {
        !           846:     LPINPLACEDATA   lpIPData;
        !           847:     
        !           848:     if (!(lpIPData = (LPINPLACEDATA) New(sizeof(INPLACEDATA))))
        !           849:         return FALSE;
        !           850:     
        !           851:     lpIPData->lpFrame       = NULL;
        !           852:     lpIPData->lpDoc         = NULL;
        !           853:     lpIPData->lpSite        = NULL; 
        !           854:     lpIPData->fInCSHelpMode = FALSE;
        !           855:     lpIPData->hOlemenu      = NULL;
        !           856:     lpIPData->hMenuShared   = NULL;
        !           857:     
        !           858:     lpServerDoc->m_lpIPData = lpIPData;
        !           859:     return TRUE;
        !           860: }
        !           861: 
        !           862: 
        !           863: void ServerDoc_FreeInPlaceData(LPSERVERDOC lpServerDoc)
        !           864: {
        !           865:     Delete(lpServerDoc->m_lpIPData);
        !           866:     lpServerDoc->m_lpIPData = NULL;
        !           867: }
        !           868: 
        !           869: 
        !           870: HRESULT ServerDoc_AssembleMenus(LPSERVERDOC lpServerDoc)
        !           871: {
        !           872:     HMENU           hMenuShared;
        !           873:     LONG FAR*       lpWidths;
        !           874:     UINT            uPosition;
        !           875:        UINT                    uPositionStart;
        !           876:     LPSERVERAPP     lpServerApp = (LPSERVERAPP) g_lpApp;
        !           877:     LPINPLACEDATA   lpIPData = lpServerDoc->m_lpIPData;
        !           878:     HRESULT         hresult;
        !           879:        BOOL                    fNoError = TRUE;
        !           880:     
        !           881:     lpWidths = lpIPData->menuGroupWidths.width;
        !           882:     hMenuShared = CreateMenu(); 
        !           883:     
        !           884:     if (hMenuShared &&
        !           885:         (hresult = lpIPData->lpFrame->lpVtbl->InsertMenus(
        !           886:             lpIPData->lpFrame, hMenuShared, 
        !           887:             &lpIPData->menuGroupWidths)) == NOERROR) {
        !           888: 
        !           889:        /* Insert EDIT group menus */
        !           890:            
        !           891:        uPosition = (UINT)lpWidths[0]; /* # of menus in the FILE group */
        !           892:        uPositionStart = uPosition;
        !           893: 
        !           894:        fNoError &= InsertMenu(
        !           895:                hMenuShared, 
        !           896:                (UINT)uPosition,
        !           897:                (UINT)(MF_BYPOSITION | MF_POPUP), 
        !           898:                (UINT)lpServerApp->m_hMenuEdit, 
        !           899:                (LPCSTR)"&Edit"
        !           900:        );
        !           901:        uPosition++;
        !           902:        
        !           903:        lpWidths[1] = uPosition - uPositionStart;
        !           904: 
        !           905:        /* Insert OBJECT group menus */
        !           906: 
        !           907:        uPosition += (UINT)lpWidths[2];
        !           908:        uPositionStart = uPosition;
        !           909: 
        !           910:        fNoError &= InsertMenu(
        !           911:                hMenuShared, 
        !           912:                (UINT)uPosition,
        !           913:                (UINT)(MF_BYPOSITION | MF_POPUP), 
        !           914:                (UINT)lpServerApp->m_hMenuLine, 
        !           915:                (LPCSTR)"&Line"
        !           916:        );
        !           917:        uPosition++;
        !           918: 
        !           919:        fNoError &= InsertMenu(
        !           920:                hMenuShared, 
        !           921:                (UINT)uPosition,
        !           922:                (UINT)(MF_BYPOSITION | MF_POPUP), 
        !           923:                (UINT)lpServerApp->m_hMenuName, 
        !           924:                (LPCSTR)"&Name"
        !           925:        );
        !           926:        uPosition++;
        !           927: 
        !           928:        fNoError &= InsertMenu(
        !           929:                hMenuShared, 
        !           930:                (UINT)uPosition,
        !           931:                (UINT)(MF_BYPOSITION | MF_POPUP), 
        !           932:                (UINT)lpServerApp->m_hMenuOptions, 
        !           933:                (LPCSTR)"&Options"
        !           934:        );
        !           935:        uPosition++;
        !           936:     
        !           937:        fNoError &= InsertMenu(
        !           938:                hMenuShared, 
        !           939:                (UINT)uPosition,
        !           940:                (UINT)(MF_BYPOSITION | MF_POPUP), 
        !           941:                (UINT)lpServerApp->m_hMenuDebug, 
        !           942:                (LPCSTR)"DbgI&Svr"
        !           943:         );
        !           944:         uPosition++;
        !           945:     
        !           946:         lpWidths[3] = uPosition - uPositionStart;
        !           947: 
        !           948:         /* Insert HELP group menus */
        !           949: 
        !           950:         uPosition += (UINT) lpWidths[4]; /* # of menus in WINDOW group */
        !           951:         uPositionStart = uPosition;
        !           952: 
        !           953:         fNoError &= InsertMenu(
        !           954:                 hMenuShared, 
        !           955:                 (UINT)uPosition,
        !           956:                 (UINT)(MF_BYPOSITION | MF_POPUP), 
        !           957:                 (UINT)lpServerApp->m_hMenuHelp,
        !           958:                 (LPCSTR)"&Help"
        !           959:         );
        !           960:         uPosition++;    
        !           961: 
        !           962:         lpWidths[5] = uPosition - uPositionStart; 
        !           963:        
        !           964:         OleDbgAssert(fNoError == TRUE);
        !           965: 
        !           966:     } else {
        !           967:         /* In-place container does not allow us to add menus to the
        !           968:         **    frame.
        !           969:         ** OLE2NOTE: even when the in-place container does NOT allow
        !           970:         **    the building of a merged menu bar, it is CRITICAL that
        !           971:         **    the in-place server still call OleCreateMenuDescriptor
        !           972:         **    passing NULL for hMenuShared. 
        !           973:         */
        !           974:         if (hMenuShared) {
        !           975:             DestroyMenu(hMenuShared);
        !           976:             hMenuShared = NULL;
        !           977:         }
        !           978:     }
        !           979:     
        !           980:     lpIPData->hMenuShared = hMenuShared;
        !           981: 
        !           982:     if (!(lpIPData->hOlemenu = OleCreateMenuDescriptor(hMenuShared, 
        !           983:                                             &lpIPData->menuGroupWidths)))
        !           984:         return ResultFromScode(E_OUTOFMEMORY);
        !           985:     
        !           986:     return NOERROR;
        !           987: }
        !           988: 
        !           989: 
        !           990: void ServerDoc_DisassembleMenus(LPSERVERDOC lpServerDoc)
        !           991: {
        !           992:     UINT             uCount;
        !           993:        UINT                    uGroup;
        !           994:        UINT                    uDeleteAt;
        !           995:     LPINPLACEDATA   lpIPData = lpServerDoc->m_lpIPData;
        !           996:     LONG FAR*       lpWidths = lpIPData->menuGroupWidths.width;
        !           997:        BOOL                    fNoError = TRUE;
        !           998:     
        !           999:     /* OLE2NOTE: even when hMenuShared is NULL (ie. the server has no
        !          1000:     **    Menu), there is still an hOleMenu created that must be destroyed.
        !          1001:     */
        !          1002:     if (lpIPData->hOlemenu) {
        !          1003:         OleDestroyMenuDescriptor (lpIPData->hOlemenu);
        !          1004:         lpIPData->hOlemenu = NULL;
        !          1005:     }
        !          1006: 
        !          1007:     if (! lpIPData->hMenuShared)
        !          1008:         return;     // no menus to be destroyed
        !          1009:     
        !          1010:     /* Remove server group menus. */
        !          1011:        uDeleteAt = 0;
        !          1012:        for (uGroup = 0; uGroup < 6; uGroup++) {
        !          1013:                uDeleteAt += (UINT)lpWidths[uGroup++];
        !          1014:                for (uCount = 0; uCount < (UINT)lpWidths[uGroup]; uCount++)
        !          1015:                        fNoError &= RemoveMenu(lpIPData->hMenuShared, uDeleteAt, 
        !          1016:                                                                MF_BYPOSITION);
        !          1017:        }
        !          1018:     
        !          1019:     /* Remove container group menus */
        !          1020:     fNoError &= (lpIPData->lpFrame->lpVtbl->RemoveMenus(
        !          1021:         lpIPData->lpFrame, 
        !          1022:         lpIPData->hMenuShared) == NOERROR);
        !          1023:         
        !          1024:        OleDbgAssert(fNoError == TRUE);
        !          1025:        
        !          1026:     DestroyMenu(lpIPData->hMenuShared);
        !          1027:     lpIPData->hMenuShared = NULL;
        !          1028: }
        !          1029: 
        !          1030: 
        !          1031: /* ServerDoc_UpdateInPlaceWindowOnExtentChange
        !          1032: ** -------------------------------------------
        !          1033: **    The size of the in-place window needs to be changed. 
        !          1034: **    calculate the size required in Client coordinates (taking into
        !          1035: **    account the current scale factor imposed by the in-place
        !          1036: **    container) and ask our in-place container to allow us to resize.
        !          1037: **    our container must call us back via
        !          1038: **    IOleInPlaceObject::SetObjectRects for the actual sizing to take
        !          1039: **    place. 
        !          1040: **    
        !          1041: **    OLE2NOTE: the rectangle that we ask for from our in-place
        !          1042: **    container is always the rectangle required for the object display
        !          1043: **    itself (in our case the size of the LineList contents). it does
        !          1044: **    NOT include the space we require for object frame adornments.
        !          1045: */
        !          1046: void ServerDoc_UpdateInPlaceWindowOnExtentChange(LPSERVERDOC lpServerDoc)
        !          1047: {
        !          1048:     SIZEL              sizelHim;
        !          1049:     SIZEL              sizelPix;
        !          1050:     RECT               rcPosRect;
        !          1051:        LPOUTLINEDOC lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !          1052:     LPLINELIST lpLL=(LPLINELIST)&lpOutlineDoc->m_LineList;
        !          1053:        HWND            hWndLL = lpLL->m_hWndListBox;
        !          1054:        LPSCALEFACTOR lpscale = (LPSCALEFACTOR)&lpOutlineDoc->m_scale;
        !          1055: 
        !          1056:     if (!lpServerDoc->m_fInPlaceActive)
        !          1057:         return;
        !          1058:        
        !          1059:        OleDoc_GetExtent((LPOLEDOC)lpServerDoc, (LPSIZEL)&sizelHim);
        !          1060: 
        !          1061:        // apply current scale factor
        !          1062:        sizelHim.cx = sizelHim.cx * lpscale->dwSxN / lpscale->dwSxD;
        !          1063:        sizelHim.cy = sizelHim.cy * lpscale->dwSxN / lpscale->dwSxD;
        !          1064:     XformSizeInHimetricToPixels(NULL, (LPSIZEL)&sizelHim, (LPSIZEL)&sizelPix);
        !          1065: 
        !          1066:     GetWindowRect(hWndLL, (LPRECT)&rcPosRect);
        !          1067:     ScreenToClient(lpServerDoc->m_hWndParent, (POINT FAR *)&rcPosRect);
        !          1068:     
        !          1069:     rcPosRect.right = rcPosRect.left + (int) sizelPix.cx;
        !          1070:     rcPosRect.bottom = rcPosRect.top + (int) sizelPix.cy;
        !          1071: 
        !          1072:     OleDbgOutRect3("ServerDoc_UpdateInPlaceWindowOnExtentChange: (PosRect)", 
        !          1073:                        (LPRECT)&rcPosRect);
        !          1074:     
        !          1075:     OLEDBG_BEGIN2("IOleInPlaceSite::OnPosRectChange called\r\n");
        !          1076:     lpServerDoc->m_lpIPData->lpSite->lpVtbl->OnPosRectChange(
        !          1077:                        lpServerDoc->m_lpIPData->lpSite,
        !          1078:                        (LPRECT) &rcPosRect
        !          1079:     );
        !          1080:     OLEDBG_END2
        !          1081: }
        !          1082: 
        !          1083: 
        !          1084: /* ServerDoc_CalcInPlaceWindowPos
        !          1085:  * ------------------------------
        !          1086:  *
        !          1087:  *     Move (and re-scale) the ServerDoc to the specified rectangle.
        !          1088:  *
        !          1089:  *     Parameters:
        !          1090:  *             lprcListBox     - rect in client coordinate in which the listbox will fit
        !          1091:  *             lprcDoc         - corresponding size of the Doc in client coordinate
        !          1092:  *
        !          1093:  */
        !          1094: void ServerDoc_CalcInPlaceWindowPos(
        !          1095:                LPSERVERDOC                     lpServerDoc, 
        !          1096:                LPRECT                          lprcListBox, 
        !          1097:                LPRECT                          lprcDoc,
        !          1098:                LPSCALEFACTOR           lpscale
        !          1099: )
        !          1100: {
        !          1101:        SIZEL sizelHim;
        !          1102:        SIZEL sizelPix;
        !          1103:        LPLINELIST lpLL;
        !          1104:        LPOUTLINEDOC lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !          1105:        LPHEADING lphead;
        !          1106:        
        !          1107:        if (!lpServerDoc || !lprcListBox || !lprcDoc)
        !          1108:                return;
        !          1109: 
        !          1110:        lphead = (LPHEADING)&lpOutlineDoc->m_heading;
        !          1111:        
        !          1112:        lpLL = OutlineDoc_GetLineList(lpOutlineDoc);
        !          1113:        OleDoc_GetExtent((LPOLEDOC)lpServerDoc, (LPSIZEL)&sizelHim);
        !          1114:        XformSizeInHimetricToPixels(NULL, &sizelHim, &sizelPix);
        !          1115: 
        !          1116:        if (sizelHim.cx == 0) {
        !          1117:                lpscale->dwSxN = 1;
        !          1118:                lpscale->dwSxD = 1;
        !          1119:        } else {
        !          1120:                lpscale->dwSxN = lprcListBox->right - lprcListBox->left;
        !          1121:                lpscale->dwSxD = sizelPix.cx;
        !          1122:        }
        !          1123:                
        !          1124:        if (sizelHim.cy == 0) {
        !          1125:                lpscale->dwSyN = 1;
        !          1126:                lpscale->dwSyD = 1;
        !          1127:        } else {
        !          1128:                lpscale->dwSyN = lprcListBox->bottom - lprcListBox->top;
        !          1129:                lpscale->dwSyD = sizelPix.cy;
        !          1130:        }
        !          1131: 
        !          1132:        lprcDoc->left = lprcListBox->left - Heading_RH_GetWidth(lphead,lpscale);
        !          1133:        lprcDoc->right = lprcListBox->right;
        !          1134:        lprcDoc->top = lprcListBox->top - Heading_CH_GetHeight(lphead,lpscale);
        !          1135:        lprcDoc->bottom = lprcListBox->bottom;
        !          1136: }
        !          1137: 
        !          1138: 
        !          1139: /* ServerDoc_ResizeInPlaceWindow
        !          1140: ** -----------------------------
        !          1141: **    Actually resize the in-place ServerDoc windows according to the
        !          1142: **    PosRect and ClipRect allowed by our in-place container.
        !          1143: **    
        !          1144: **    OLE2NOTE: the PosRect rectangle that our in-place container tells
        !          1145: **    us is always the rectangle required for the object display
        !          1146: **    itself (in our case the size of the LineList contents). it does
        !          1147: **    NOT include the space we require for object frame adornments.
        !          1148: */
        !          1149: void ServerDoc_ResizeInPlaceWindow(
        !          1150:                LPSERVERDOC                     lpServerDoc, 
        !          1151:         LPCRECT             lprcPosRect,
        !          1152:         LPCRECT             lprcClipRect
        !          1153: )
        !          1154: {
        !          1155:     LPOUTLINEDOC lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !          1156:     LPLINELIST   lpLL = (LPLINELIST)&lpOutlineDoc->m_LineList;
        !          1157:        SCALEFACTOR      scale;
        !          1158:        RECT             rcDoc;
        !          1159:     POINT        ptOffset;
        !          1160: 
        !          1161:        /* OLE2NOTE: calculate the space needed for our object frame
        !          1162:        **    adornments. our in-place container tells us the size that our
        !          1163:        **    object should take in window client coordinates
        !          1164:        **    (lprcPosRect). the rectangle cooresponds to the size that our
        !          1165:        **    LineList ListBox should be. our Doc window must the correct
        !          1166:        **    amount larger to accomodate our row/column headings.
        !          1167:        **    then move all windows into position.
        !          1168:        */
        !          1169:        ServerDoc_CalcInPlaceWindowPos(
        !          1170:                        lpServerDoc, 
        !          1171:                        (LPRECT)lprcPosRect, 
        !          1172:                        (LPRECT)&rcDoc,
        !          1173:                        (LPSCALEFACTOR)&scale
        !          1174:        );
        !          1175: 
        !          1176:     /* OLE2NOTE: we need to honor the lprcClipRect specified by our
        !          1177:     **    in-place container. we must NOT draw outside of the ClipRect.
        !          1178:     **    in order to achieve this, we will size the hatch window to be
        !          1179:     **    exactly the size that should be visible (rcVisRect). the
        !          1180:     **    rcVisRect is defined as the intersection of the full size of
        !          1181:     **    the in-place server window and the lprcClipRect.
        !          1182:     **    the ClipRect could infact clip the HatchRect on the
        !          1183:     **    right/bottom and/or on the top/left. if it is clipped on the
        !          1184:     **    right/bottom then it is sufficient to simply resize the hatch
        !          1185:     **    window. but if the HatchRect is clipped on the top/left then
        !          1186:     **    we must "move" the ServerDoc window (child of HatchWindow) by
        !          1187:     **    the delta that was clipped. the window origin of the
        !          1188:     **    ServerDoc window will then have negative coordinates relative
        !          1189:     **    to its parent HatchWindow.
        !          1190:     */
        !          1191:     SetHatchWindowSize(
        !          1192:             lpServerDoc->m_hWndHatch, 
        !          1193:             (LPRECT)&rcDoc,
        !          1194:             (LPRECT)lprcClipRect, 
        !          1195:             (LPPOINT)&ptOffset
        !          1196:     );
        !          1197: 
        !          1198:     // shift Doc window to account for hatch frame being drawn
        !          1199:        OffsetRect((LPRECT)&rcDoc, ptOffset.x, ptOffset.y);
        !          1200:     
        !          1201:     // move/size/set scale factor of ServerDoc window.
        !          1202:        OutlineDoc_SetScaleFactor(
        !          1203:                        lpOutlineDoc, (LPSCALEFACTOR)&scale, (LPRECT)&rcDoc);
        !          1204: }
        !          1205: 
        !          1206: 
        !          1207: 
        !          1208: /* ServerDoc_GetTopInPlaceFrame
        !          1209: ** ----------------------------
        !          1210: **    returns NON-AddRef'ed pointer to Top In-Place Frame interface
        !          1211: */
        !          1212: LPOLEINPLACEFRAME ServerDoc_GetTopInPlaceFrame(LPSERVERDOC lpServerDoc)
        !          1213: {
        !          1214:        if (lpServerDoc->m_lpIPData) 
        !          1215:                return lpServerDoc->m_lpIPData->lpFrame;
        !          1216:        else 
        !          1217:                return NULL;
        !          1218: }
        !          1219: 
        !          1220: void ServerDoc_GetSharedMenuHandles(
        !          1221:                LPSERVERDOC     lpServerDoc,
        !          1222:                HMENU FAR*              lphSharedMenu,
        !          1223:                HOLEMENU FAR*   lphOleMenu
        !          1224: )
        !          1225: {
        !          1226:        if (lpServerDoc->m_lpIPData) {
        !          1227:                *lphSharedMenu = lpServerDoc->m_lpIPData->hMenuShared;
        !          1228:                *lphOleMenu = lpServerDoc->m_lpIPData->hOlemenu;
        !          1229:        } else {
        !          1230:                *lphSharedMenu = NULL;
        !          1231:                *lphOleMenu = NULL;
        !          1232:        }
        !          1233: }
        !          1234: 
        !          1235:        
        !          1236: void ServerDoc_AddFrameLevelUI(LPSERVERDOC lpServerDoc)
        !          1237: {
        !          1238:        LPOUTLINEAPP lpOutlineApp = (LPOUTLINEAPP)g_lpApp;
        !          1239:        LPSERVERAPP lpServerApp = (LPSERVERAPP)g_lpApp;
        !          1240:        LPOUTLINEDOC lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !          1241:        LPOLEINPLACEFRAME lpTopIPFrame=ServerDoc_GetTopInPlaceFrame(lpServerDoc);
        !          1242:        HMENU                   hSharedMenu;                    // combined obj/cntr menu
        !          1243:        HOLEMENU                hOleMenu;                               // returned by OleCreateMenuDesc.
        !          1244: 
        !          1245:        ServerDoc_GetSharedMenuHandles(
        !          1246:                        lpServerDoc, 
        !          1247:                        &hSharedMenu,
        !          1248:                        &hOleMenu
        !          1249:        );
        !          1250: 
        !          1251:        lpTopIPFrame->lpVtbl->SetMenu(
        !          1252:                        lpTopIPFrame, 
        !          1253:                        hSharedMenu, 
        !          1254:                        hOleMenu,
        !          1255:                        lpOutlineDoc->m_hWndDoc
        !          1256:        );
        !          1257:     
        !          1258:     lpOutlineApp->m_hAccel = lpServerApp->m_hAccelIPSvr;
        !          1259:     lpOutlineApp->m_hWndAccelTarget = lpOutlineDoc->m_hWndDoc;
        !          1260: 
        !          1261: #if defined( USE_FRAMETOOLS )
        !          1262:        ServerDoc_AddFrameLevelTools(lpServerDoc);
        !          1263: 
        !          1264:     // update toolbar button enable states
        !          1265:     OutlineDoc_UpdateFrameToolButtons(lpOutlineDoc);
        !          1266: #endif  
        !          1267: }
        !          1268: 
        !          1269:        
        !          1270: void ServerDoc_AddFrameLevelTools(LPSERVERDOC lpServerDoc)
        !          1271: {
        !          1272:        LPOUTLINEAPP    lpOutlineApp = (LPOUTLINEAPP)g_lpApp;
        !          1273:        LPSERVERAPP             lpServerApp = (LPSERVERAPP)g_lpApp;
        !          1274:        LPOUTLINEDOC    lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !          1275:        LPOLEINPLACEFRAME lpTopIPFrame=ServerDoc_GetTopInPlaceFrame(lpServerDoc);
        !          1276: 
        !          1277: #if defined( USE_FRAMETOOLS )
        !          1278:     HWND            hWndFrame;
        !          1279: 
        !          1280:        FrameTools_Enable(lpOutlineDoc->m_lpFrameTools, TRUE);
        !          1281: 
        !          1282:        // if not in-place UI active, add our tools to our own frame.
        !          1283:        if (! lpServerDoc->m_fUIActive) {
        !          1284:                OutlineDoc_AddFrameLevelTools(lpOutlineDoc);
        !          1285:                return;
        !          1286:        }
        !          1287: 
        !          1288:        if ((hWndFrame = OutlineApp_GetFrameWindow(lpOutlineApp)) == NULL) {
        !          1289:                /* we could NOT get a valid frame window, so POP our tools up. */
        !          1290: 
        !          1291:         /* OLE2NOTE: since we are poping up our tools, we MUST inform
        !          1292:         **    the top in-place frame window that we need NO tool space
        !          1293:         **    BUT that it should NOT put its own tools up. if we were
        !          1294:         **    to pass NULL instead of (0,0,0,0), then the container
        !          1295:         **    would have the option to leave its own tools up.
        !          1296:         */
        !          1297:         lpTopIPFrame->lpVtbl->SetBorderSpace(
        !          1298:                 lpTopIPFrame, 
        !          1299:                 (LPCBORDERWIDTHS)&g_rectNull
        !          1300:         );
        !          1301:                FrameTools_PopupTools(lpOutlineDoc->m_lpFrameTools);
        !          1302:        } else {
        !          1303: 
        !          1304:                /* OLE2NOTE: we need to negotiate for space and attach our frame
        !          1305:                **    level tools to the top-level in-place container's frame window.
        !          1306:                */
        !          1307:                FrameTools_AttachToFrame(lpOutlineDoc->m_lpFrameTools, hWndFrame);
        !          1308: 
        !          1309:                FrameTools_NegotiateForSpaceAndShow(
        !          1310:                                lpOutlineDoc->m_lpFrameTools, 
        !          1311:                                NULL,
        !          1312:                                lpTopIPFrame
        !          1313:                );              
        !          1314:        }
        !          1315: 
        !          1316: #else  // ! USE_FRAMETOOLS
        !          1317:        /* OLE2NOTE: if you do NOT use frame tools, you MUST inform the top
        !          1318:        **    in-place frame window so that it can put back its own tools.
        !          1319:        */
        !          1320:        lpTopIPFrame->lpVtbl->SetBorderSpace(lpIPData->lpFrame, NULL);
        !          1321: #endif // ! USE_FRAMETOOLS
        !          1322: }
        !          1323: 
        !          1324: 
        !          1325: #if defined( USE_FRAMETOOLS )
        !          1326: 
        !          1327: void ServerDoc_RemoveFrameLevelTools(LPSERVERDOC lpServerDoc) 
        !          1328: {
        !          1329:        LPOUTLINEDOC lpOutlineDoc = (LPOUTLINEDOC)lpServerDoc;
        !          1330:        OleDbgAssert(lpOutlineDoc->m_lpFrameTools != NULL);
        !          1331: 
        !          1332:        FrameTools_Enable(lpOutlineDoc->m_lpFrameTools, FALSE);
        !          1333: }
        !          1334: #endif // USE_FRAMETOOLS
        !          1335: 
        !          1336: 
        !          1337: 
        !          1338: void ServerDoc_UIActivate (LPSERVERDOC lpServerDoc) 
        !          1339: {
        !          1340:        if (lpServerDoc->m_fInPlaceActive && !lpServerDoc->m_fUIActive) {
        !          1341:                ServerDoc_DoInPlaceActivate(lpServerDoc,
        !          1342:                                OLEIVERB_UIACTIVATE,
        !          1343:                                NULL /*lpmsg*/,
        !          1344:                                lpServerDoc->m_lpOleClientSite
        !          1345:                );
        !          1346:         OutlineDoc_ShowWindow((LPOUTLINEDOC)lpServerDoc);
        !          1347:        }       
        !          1348: }
        !          1349: 
        !          1350: 
        !          1351: 
        !          1352: #endif  // INPLACE_SVR
        !          1353: 

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.