_BUILDING AN OLE SERVER USING VISUAL C++ 2.0_ by John LaPlante Listing One /*------------------------- SRVRDOC.H ----------------------------*/ // This is the CDocument-derived class that encapsulates a picture // object and forwards all drawing messages to it. class CGIFServerItem; class XPictureBase; class CGIFServerDoc : public COleServerDoc { protected: // create from serialization only CGIFServerDoc(); DECLARE_DYNCREATE(CGIFServerDoc) // Attributes public: CGIFServerItem* GetEmbeddedItem() { return (CGIFServerItem*)COleServerDoc::GetEmbeddedItem(); } // Operations public: // Overrides // ClassWizard generated virtual function overrides //{{AFX_VIRTUAL(CGIFServerDoc) public: virtual BOOL OnNewDocument(); virtual BOOL OnOpenDocument(LPCTSTR lpszPathName); virtual void DeleteContents(); protected: virtual COleServerItem* OnGetEmbeddedItem(); //}}AFX_VIRTUAL // Implementation public: virtual ~CGIFServerDoc(); virtual void Serialize(CArchive& ar); #ifdef _DEBUG virtual void AssertValid() const; virtual void Dump(CDumpContext& dc) const; #endif protected: // Generated message map functions protected: //{{AFX_MSG(CGIFServerDoc) // NOTE -the ClassWizard will add and remove member functions here. // DO NOT EDIT what you see in these blocks of generated code ! //}}AFX_MSG DECLARE_MESSAGE_MAP() // Generated OLE dispatch map functions //{{AFX_DISPATCH(CGIFServerDoc) // NOTE -the ClassWizard will add and remove member functions here. // DO NOT EDIT what you see in these blocks of generated code ! //}}AFX_DISPATCH DECLARE_DISPATCH_MAP() // The following lines of code were added by hand: public: void draw(CDC &, const RECT &); private: XPictureBase * pPicture; }; Listing Two /*------------------------- SRVRDOC.CPP --------------------------*/ #include "stdafx.h" #include "gifserv.h" #include "srvrdoc.h" #include "srvritem.h" #include "gifpict.hpp" #ifdef _DEBUG #undef THIS_FILE static char BASED_CODE THIS_FILE[] = __FILE__; #endif /////// CGIFServerDoc //////// IMPLEMENT_DYNCREATE(CGIFServerDoc, COleServerDoc) BEGIN_MESSAGE_MAP(CGIFServerDoc, COleServerDoc) //{{AFX_MSG_MAP(CGIFServerDoc) // NOTE - the ClassWizard will add and remove mapping macros here. // DO NOT EDIT what you see in these blocks of generated code! //}}AFX_MSG_MAP END_MESSAGE_MAP() BEGIN_DISPATCH_MAP(CGIFServerDoc, COleServerDoc) //{{AFX_DISPATCH_MAP(CGIFServerDoc) // NOTE - the ClassWizard will add and remove mapping macros here. // DO NOT EDIT what you see in these blocks of generated code! //}}AFX_DISPATCH_MAP END_DISPATCH_MAP() ////// CGIFServerDoc construction/destruction ////// CGIFServerDoc::CGIFServerDoc() { // TODO: add one-time construction code here pPicture = NULL; EnableAutomation(); AfxOleLockApp(); } CGIFServerDoc::~CGIFServerDoc() { AfxOleUnlockApp(); } BOOL CGIFServerDoc::OnNewDocument() { if (!COleServerDoc::OnNewDocument()) return FALSE; // TODO: add reinitialization code here // (SDI documents will reuse this document) TRACE("New Document\n"); ASSERT(pPicture == NULL); return TRUE; } ///// CGIFServerDoc server implementation ///// COleServerItem* CGIFServerDoc::OnGetEmbeddedItem() { // OnGetEmbeddedItem is called by the framework to get the COleServerItem // that is associated with the document. It is only called when necessary. CGIFServerItem* pItem = new CGIFServerItem(this); ASSERT_VALID(pItem); return pItem; } ///// CGIFServerDoc serialization ///// void CGIFServerDoc::Serialize(CArchive& ar) { if (ar.IsStoring()) { // TODO: add storing code here TRACE("Storing serial document\n"); } else { // TODO: add loading code here TRACE("Loading serial document\n"); ASSERT(pPicture == NULL); pPicture = new XGIFPicture(*ar.GetFile()); } } ///// CGIFServerDoc diagnostics ///// #ifdef _DEBUG void CGIFServerDoc::AssertValid() const { COleServerDoc::AssertValid(); } void CGIFServerDoc::Dump(CDumpContext& dc) const { COleServerDoc::Dump(dc); } #endif //_DEBUG ///// CGIFServerDoc commands ///// BOOL CGIFServerDoc::OnOpenDocument(LPCTSTR lpszPathName) { if (!COleServerDoc::OnOpenDocument(lpszPathName)) return FALSE; // TODO: Add your specialized creation code here TRACE("Open Document\n"); return TRUE; } // This function was added automatically by ClassWizard. void CGIFServerDoc::DeleteContents() { // TODO: Add your specialized code here or call the base class TRACE("Delete Document Contents\n"); // These two lines were added manually to free the picture object delete pPicture; pPicture = NULL; COleServerDoc::DeleteContents(); } // This function was added by hand. ClassWizard could not do it. It basically // passes the WM_PAINT message along to the picture object contained herein. void CGIFServerDoc::draw(CDC & dc, const RECT & r2) { if (pPicture != NULL) pPicture->draw(dc, r2); } Listing Three /*------------------------- PICTURE.HPP --------------------------*/ // Abstract base class for all types of picture objects. #ifndef __PICTURE_HPP #define __PICTURE_HPP #include #include "error.hpp" class XPictureBase { protected: XeStatus mnStatus; public: XPictureBase(); virtual ~XPictureBase(); // Non-virtual member functions XeStatus status() const; BOOL isOK() const; // Pure virtual member functions virtual short height() const = 0; virtual short width() const = 0; virtual XeStatus draw(CDC & destDC, const RECT &destRect) = 0; }; #endif // __PICTURE_HPP Listing Four /*------------------------- GIFPICT.HPP --------------------------*/ // Class XGIFPicture, creates picture objects derived from GIF // image files on disk. #ifndef __GIFPICT_HPP #define __GIFPICT_HPP #include "picture.hpp" class XGIFPicture : public XPictureBase { public: XGIFPicture(CFile & file); virtual ~XGIFPicture(); // Inherited pure virtuals implemented in this class virtual short height() const; virtual short width() const; virtual XeStatus draw(CDC & destDC, const RECT &destRect); private: // Private member variables long mlImageSize; // Size of the image in bytes unsigned short munBitsPerPixel; // Usually 1, 4 or 8 unsigned short munHeight; // Size of image in pixels unsigned short munWidth; // "" BITMAPINFO * mpsDibHeader; // DIB Header and palette unsigned char * mpPictureData; // Ptr to the DIB pixel data // Private member functions XeStatus loadImage(unsigned char * rawImage); XeStatus ParseGIFHeader( unsigned char * pGIF, unsigned char * & newPtr); }; #endif //__GIFPICT_HPP