Link to home
Start Free TrialLog in
Avatar of amnav
amnav

asked on

Copying a bitmap to the clipboard

Hi,

I'm working with VC++ (without using MFC).
I'm trying to pass a bitmap ,that I created, to the clipboard, so other application (VB application) can present it.

Any idea how to do that ?


Many thanks?
Avatar of Mirkwood
Mirkwood

fROM THE msDN

ICCLIP.C
/***************************************************************************      *                                                                         *      *  MODULE      : ICClip.C                                                 *      *                                                                         *      *  DESCRIPTION : Clipboard functions for ImagEdit                         *      *                                                                         *      *  FUNCTIONS   : CopyImageClip ()  - Copies selected portion of image to  *      *                                    the clipboard.                       *      *                                                                         *      *                PasteImageClip () - Pastes the clipboard image to        *      *                                    selected portion of edit image.      *      *                                                                         *      *                                                                         *      *  HISTORY     : 6/21/89 - created by LR                                  *      *                                                                         *      ***************************************************************************/          #include "imagedit.h"     #include "dialogs.h"     #include "iehelp.h"       #include <windowsx.h>          /*==========================================================================       |ImagEdit's clipboard data is in two formats:                              |       |        a) a standard CF_BITMAP format  and                               |       |        b) a private ImagEdit format described below.                     |       |                                                                          |       |The private ImagEdit format data consists of:                             |       |   1.  a DWORD describing screen color when image was sent to clipboard   |       |       followed by...                                                     |       |   2.  the DIB bits of the monochrome AND image (in ghdcANDMask).         |       |                                                                          |       |The CF_BITMAP format consists of the image bitmap (the combined XOR and   |       |AND images in ghdcImage for icons and cursors).                           |       |                                                                          |       |This information is sufficient to re-create the image correctly during    |       |paste even if the screen viewing color is subsequently changed.           |       |                                                                          |       |Both formats are created if the image being edited is an icon or a cursor.|       |Only the CF_BITMAP format is created if a bitmap is being edited.         |       ==========================================================================*/          /****************************************************************************      *                                                                          *      *  FUNCTION   : BOOL PASCAL CopyImageClip(fBitmap)                         *      *                                                                          *      *  PURPOSE    : Copies the information from the selected area of image to  *      *               the clipboard.                                             *      *                                                                          *      *  SIDE EFFECTS: may change contents of the clipboard. The "pick" or clip  *      *                rectangle is reset to cover the entire image.             *      *                                                                          *      ****************************************************************************/          BOOL CopyImageClip(VOID)     {         HCURSOR hcurOld;         HBITMAP hStdBitmap;         HBITMAP hPrivBitmap;         HDC hStdDC;         HDC hPrivDC;         HANDLE hOldSObj;         HANDLE hOldPObj;         HANDLE hPriv;         LPSTR lpPriv;              hcurOld = SetCursor(hcurWait);              /* create a temp. bitmap and DC for the standard clipboard format          * along the same lines as the image bitmap          */         hStdDC = CreateCompatibleDC(ghdcImage);         hStdBitmap = MyCreateBitmap(ghdcImage, gcxPick, gcyPick, 16);         hOldSObj = SelectObject(hStdDC, hStdBitmap);              /* blt the image bits into standard format DC */         BitBlt(hStdDC, 0, 0, gcxPick, gcyPick, ghdcImage,                 grcPick.left, grcPick.top, SRCCOPY);         SelectObject(hStdDC, hOldSObj);              if (giType != FT_BITMAP) {             /* for icons and cursors, create a temp. DC and bitmap for the AND             * mask and blt the mask bits into it.             */             hPrivDC = CreateCompatibleDC(ghdcANDMask);             hPrivBitmap = CreateCompatibleBitmap(ghdcANDMask, gcxPick, gcyPick);             hOldPObj = SelectObject(hPrivDC, hPrivBitmap);             BitBlt(hPrivDC, 0, 0, gcxPick, gcyPick, ghdcANDMask,                     grcPick.left, grcPick.top, SRCCOPY);                  /* Allocate a buffer for the private ImagEdit format */             hPriv = GlobalAlloc(GMEM_MOVEABLE | GMEM_DDESHARE,                     (DWORD)((gcxPick + 31) >> 3) * gcyPick + sizeof(DWORD));             if (!hPriv) {                 DeleteDC(hStdDC);                 DeleteObject(hStdBitmap);                 DeleteDC(hPrivDC);                 DeleteObject(hPrivBitmap);                 return FALSE;             }                  lpPriv = (LPSTR)GlobalLock(hPriv);                  /* Fill in the first DWORD with the screen color information */             *((DWORD FAR *)lpPriv) = grgbScreen;                  /* Get the mask bits into the buffer */             GetBitmapBits(hPrivBitmap, (DWORD)((gcxPick + 31) >> 3) * gcyPick,                     (LPSTR)lpPriv + sizeof(DWORD));                  SelectObject(hPrivDC, hOldPObj);             DeleteObject(hPrivBitmap);             DeleteDC(hPrivDC);         }              /* Open clipboard and clear it of it's contents */         if (!OpenClipboard(ghwndMain)) {             DeleteDC(hStdDC);             return(FALSE);         }         EmptyClipboard();              if (giType != FT_BITMAP) {             /* set the private ImagEdit format data into the clipboard */             if (!SetClipboardData(ClipboardFormat, hPriv)) {                 DeleteDC(hStdDC);                 GlobalUnlock(hPriv);                 GlobalFree(hPriv);                 CloseClipboard();                 return(FALSE);             }             GlobalUnlock(hPriv);         }         /* set the standard CF_BITMAP format data in the clipboard */         if (!SetClipboardData(CF_BITMAP, hStdBitmap)) {             DeleteDC(hStdDC);             GlobalFree(hPriv);  //   hPriv may not have been initialized (if giType == BITMAP).             CloseClipboard();             return(FALSE);         }              CloseClipboard();         DeleteDC(hStdDC);              /*          * Reset pick rectangle to cover entire image.          */         PickSetRect(0, 0, gcxImage - 1, gcyImage - 1);              /*          * Erase the drag rectangle.          */         WorkUpdate();              SetCursor(hcurOld);              return TRUE;     }                    /************************************************************************     * PasteImageClip     *     * Pastes an image from the clipboard to the current image.     *     * It is assumed that this routine will not be called unless an     * image is currently being edited.     *     * The pick rectangle is reset to cover the entire image if the     * paste is successful.     *     * Basic outline of how Paste is done in ImagEdit.     *     * Find out what format is available in the clipboard:     *    a. CF_BITMAP only     *       --------------     *       case 1: Pasting to an icon or cursor     *                 * We don't have any screen color information.     *                   Make the mask bits opaque and blt. the bitmap to     *                   ghdcImage.     *     *       case 2: Pasting to a bitmap     *                 * Blt the bitmap to the image DC.     *     *    b. both ImagEdit and CF_BITMAP     *       ---------------------------     *       case 1: Pasting to an icon or cursor     *                 * Recover the image from the AND and screen color     *                   data (in ImagEdit) and the combined image bitmap     *                   (in CF_BITMAP). Use the information to make the     *                   neccessary changes if the screen viewing color was     *                   changed between Copy and Paste.     *     *       case 2: Pasting to a bitmap     *                 * Blt the CF_BITMAP data to the image DC.     *     * If the destination image differs in dimensions from     * source image, the source image is stretched or clipped to that of     * destination, depending on preference     *     * History:     *     ************************************************************************/          BOOL PasteImageClip(VOID)     {         HCURSOR hcurOld;         INT cxClip;         INT cyClip;         INT cxTarget;         INT cyTarget;         INT cxSource;         INT cySource;         DWORD rgbClipScreen;         BOOL fIEFormatFound;         HANDLE hClipData;         LPSTR lpClipData;         BITMAP bmClip;         HDC hdcClip;         HBITMAP hbmClip;         HBITMAP hbmClipOld;         HDC hdcClipAND;         HBITMAP hbmClipAND;         HBITMAP hbmClipANDOld;         HDC hdcClipAND16;         HBITMAP hbmClipAND16;         HBITMAP hbmClipAND16Old;         HDC hdcTarget;         HBITMAP hbmTarget;         HBITMAP hbmTargetOld;         HDC hdcTargetAND16;         HBITMAP hbmTargetAND16;         HBITMAP hbmTargetAND16Old;         HDC hdcTargetAND;         HBITMAP hbmTargetAND;         HBITMAP hbmTargetANDOld;              hcurOld = SetCursor(hcurWait);              if (!OpenClipboard(ghwndMain)) {             Message(MSG_NOCLIPBOARD);             goto Error1;         }              if (!(hbmClip = GetClipboardData(CF_BITMAP))) {             Message(MSG_NOCLIPBOARDFORMAT);             goto Error2;         }              GetObject(hbmClip, sizeof(BITMAP), (LPSTR)&bmClip);         cxClip = (INT)bmClip.bmWidth;         cyClip = (INT)bmClip.bmHeight;              /*          * If the dimensions of the current pick rectangle don't match          * the bitmap being pasted, ask the user if they want to stretch          * or clip the pasted image.          */         cxTarget = gcxPick;         cyTarget = gcyPick;         cxSource = cxClip;         cySource = cyClip;         if (gcxPick != cxClip || gcyPick != cyClip) {             if (DlgBox(DID_PASTEOPTIONS, (WNDPROC)PasteOptionsDlgProc) == IDCANCEL) {                 goto Error2;             }                  /*              * If clipping and the clipboard dimensions differ from the              * selected pick rectangle, then either the target dimensions              * or the source dimensions need to be sized down.              */             if (!fStretchClipboardData) {                 if (cxClip < gcxPick)                     cxTarget = cxClip;                 else                     cxSource = gcxPick;                      if (cyClip < gcyPick)                     cyTarget = cyClip;                 else                     cySource = gcyPick;             }         }              /*          * Update the undo buffer now that we are committed to the paste.          */         ImageUpdateUndo();              /*          * Determine if the private ImagEdit clipboard format is available.          */         fIEFormatFound = IsClipboardFormatAvailable(ClipboardFormat);              if (giType != FT_BITMAP && fIEFormatFound) {             /*              * Get the AND mask bitmap and the old screen color out of              * the private format.              */             hClipData = GetClipboardData(ClipboardFormat);             lpClipData = (LPSTR)GlobalLock(hClipData);             rgbClipScreen = *((DWORD FAR *)lpClipData);             hdcClipAND = CreateCompatibleDC(ghdcImage);             hbmClipAND = CreateBitmap(cxClip, cyClip, (BYTE)1, (BYTE)1,                     (LPSTR)lpClipData + sizeof(DWORD));             hbmClipANDOld = SelectObject(hdcClipAND, hbmClipAND);                  /*              * Create a color bitmap for temporary use.              */             hdcClipAND16 = CreateCompatibleDC(ghdcImage);             hbmClipAND16 = MyCreateBitmap(ghdcImage, cxSource, cySource, 16);             hbmClipAND16Old = SelectObject(hdcClipAND16, hbmClipAND16);                  /*              * Blt the AND mask onto the color bitmap.              */             BitBlt(hdcClipAND16, 0, 0, cxSource, cySource, hdcClipAND,                     0, 0, SRCCOPY);                  /*              * Create the color target AND mask bitmap.              */             hdcTargetAND16 = CreateCompatibleDC(ghdcImage);             hbmTargetAND16 = MyCreateBitmap(ghdcImage, cxTarget, cyTarget, 16);             hbmTargetAND16Old = SelectObject(hdcTargetAND16, hbmTargetAND16);                  /*              * StretchBlt from the color AND mask bitmap to the color target              * AND mask bitmap.  The blt must be done from a color bitmap to              * a color bitmap, and the stretch blt mode must be set to              * COLORONCOLOR.  All this is necessary so that the AND mask              * stays exactly in sync with the stretch blt of the color              * (XOR) mask.  If these steps are not done correctly, shrinking              * an image with screen colored pixels in it can cause problems,              * because the stretch blt will use a slightly different              * algorithm to compress the monochrome AND mask and the color              * XOR mask.              */             SetStretchBltMode(hdcTargetAND16, COLORONCOLOR);             SetStretchBltMode(hdcClipAND16, COLORONCOLOR);     //             StretchBlt(hdcTargetAND16, 0, 0, cxTarget, cyTarget, hdcClipAND16,                     0, 0, cxSource, cySource, SRCCOPY);                  /*              * Create the monochrome target AND mask bitmap.              */             hdcTargetAND = CreateCompatibleDC(ghdcImage);             hbmTargetAND = MyCreateBitmap(ghdcImage, cxTarget, cyTarget, 2);             hbmTargetANDOld = SelectObject(hdcTargetAND, hbmTargetAND);                  /*              * Blt the color AND mask onto the monochrome AND mask.              * The monochrome AND mask is the one that we will use              * later.  It must be monochrome or the ImageDCSeparate              * and ImageDCCombine functions will not work properly.              */             BitBlt(hdcTargetAND, 0, 0, cxTarget, cyTarget, hdcTargetAND16,                     0, 0, SRCCOPY);                  /*              * Cleanup.              */             SelectObject(hdcTargetAND16, hbmTargetAND16Old);             DeleteObject(hbmTargetAND16);             DeleteDC(hdcTargetAND16);             SelectObject(hdcClipAND16, hbmClipAND16Old);             DeleteObject(hbmClipAND16);             DeleteDC(hdcClipAND16);             SelectObject(hdcClipAND, hbmClipANDOld);             DeleteObject(hbmClipAND);             DeleteDC(hdcClipAND);             GlobalUnlock(hClipData);         }              /*          * Get the clipboard bitmap into a DC.          */         hdcClip = CreateCompatibleDC(ghdcImage);         hbmClipOld = SelectObject(hdcClip, hbmClip);              /*          * Create the target bitmap.          */         hdcTarget = CreateCompatibleDC(ghdcImage);         hbmTarget = MyCreateBitmap(ghdcImage, cxTarget, cyTarget, 16);         hbmTargetOld = SelectObject(hdcTarget, hbmTarget);              /*          * StretchBlt the bitmap onto the target.          */         SetStretchBltMode(hdcTarget, COLORONCOLOR);         SetStretchBltMode(hdcClip, COLORONCOLOR);     //         StretchBlt(hdcTarget, 0, 0, cxTarget, cyTarget, hdcClip, 0, 0,                 cxSource, cySource, SRCCOPY);              /*          * Handle some special cases.          */         if (giType == FT_BITMAP || !fIEFormatFound) {             /*              * The image we are pasting into is either a bitmap, or              * there does not exist an AND mask in the clipboard.              */             if (gnColors == 2) {                 /*                  * We are pasting to a mono image.  We must convert the                  * colors in the clipboard bitmap into monochrome.                  */                 ImageDCMonoBlt(hdcTarget, cxTarget, cyTarget);             }         }         else {             /*              * We are pasting into an icon or cursor image and we have              * available an AND mask.  Is the current image monochrome?              */             if (gnColors == 2) {                 /*                  * Remove the old screen/inverse colors from the image,                  * convert it to monochrome, then put back in the                  * current screen/inverse colors.                  */                 ImageDCSeparate(hdcTarget, cxTarget, cyTarget, hdcTargetAND,                         rgbClipScreen);                 ImageDCMonoBlt(hdcTarget, cxTarget, cyTarget);                 ImageDCCombine(hdcTarget, cxTarget, cyTarget, hdcTargetAND);             }             /*              * Does the screen color specified in the clipboard              * differ from the current screen color?              */             else if (rgbClipScreen != grgbScreen) {                 /*                  * Remove the old screen/inverse colors, then put back                  * in the current ones.                  */                 ImageDCSeparate(hdcTarget, cxTarget, cyTarget, hdcTargetAND,                         rgbClipScreen);                 ImageDCCombine(hdcTarget, cxTarget, cyTarget, hdcTargetAND);             }         }              /*          * Blt the clipboard image to the proper rectangle in the current image.          */         BitBlt(ghdcImage, grcPick.left, grcPick.top,                 cxTarget, cyTarget, hdcTarget, 0, 0, SRCCOPY);              /*          * If the current image is an icon or cursor, we must take care          * of the AND mask also.          */         if (giType != FT_BITMAP) {             /*              * Is there an AND mask in the clipboard to use?              */             if (fIEFormatFound) {                 /*                  * Blt it into the current image's AND mask.                  */                 BitBlt(ghdcANDMask, grcPick.left, grcPick.top,                         cxTarget, cyTarget, hdcTargetAND, 0, 0, SRCCOPY);             }             else {                 /*                  * Make the AND mask opaque, because there is no                  * screen color information.                  */                 PatBlt(ghdcANDMask, grcPick.left, grcPick.top,                         cxTarget, cyTarget, BLACKNESS);             }         }              /*          * Cleanup.          */         SelectObject(hdcTarget, hbmTargetOld);         DeleteObject(hbmTarget);         DeleteDC(hdcTarget);              if (giType != FT_BITMAP && fIEFormatFound) {             SelectObject(hdcTargetAND, hbmTargetANDOld);             DeleteObject(hbmTargetAND);             DeleteDC(hdcTargetAND);         }              SelectObject(hdcClip, hbmClipOld);         DeleteDC(hdcClip);              CloseClipboard();              /*          * Update the View and workspace windows.          */         ViewUpdate();              /*          * Reset pick rectangle to cover entire image.          */         PickSetRect(0, 0, gcxImage - 1, gcyImage - 1);              fImageDirty = TRUE;              SetCursor(hcurOld);              return TRUE;          Error2:         CloseClipboard();          Error1:         SetCursor(hcurOld);              return FALSE;     }                    /************************************************************************     * PasteOptionsDlgProc     *     * Proc for the dialog that asks the user whether they want to clip     * or stretch the bitmap being pasted in.     *     * Upon return with an IDOK value, the fStretchClipboardData global     * will be TRUE if they want to stretch, or FALSE if they want to clip.     *     * History:     *     ************************************************************************/          DIALOGPROC PasteOptionsDlgProc(         HWND hwnd,         UINT msg,         WPARAM wParam,         LPARAM lParam)     {         switch (msg) {             case WM_INITDIALOG:                 CheckRadioButton(hwnd, DID_PASTEOPTIONSSTRETCH,                         DID_PASTEOPTIONSCLIP,                         fStretchClipboardData ?                         DID_PASTEOPTIONSSTRETCH : DID_PASTEOPTIONSCLIP);                      CenterWindow(hwnd);                      break;                  case WM_COMMAND:                 switch (GET_WM_COMMAND_ID(wParam, lParam)) {                     case IDOK :                         if (IsDlgButtonChecked(hwnd, DID_PASTEOPTIONSSTRETCH))                             fStretchClipboardData = TRUE;                         else                             fStretchClipboardData = FALSE;                              EndDialog(hwnd, IDOK);                         break;                          case IDCANCEL:                         EndDialog(hwnd, IDCANCEL);                         break;                          case IDHELP:                         WinHelp(ghwndMain, gszHelpFile, HELP_CONTEXT,                                 HELPID_PASTEOPTIONS);                         break;                 }                      break;                  default:                 return FALSE;         }              return TRUE;     }                    /************************************************************************     * PickSetRect     *     * Sets the globals for the picking rectangle size.  This affects     * what is copied into the clipboard.     *     * Arguments:     *     * History:     *     ************************************************************************/          VOID PickSetRect(         INT xLeft,         INT yTop,         INT xRight,         INT yBottom)     {         SetRect(&grcPick, xLeft, yTop, xRight, yBottom);         gcxPick = (grcPick.right - grcPick.left) + 1;         gcyPick = (grcPick.bottom - grcPick.top) + 1;     }
 

cool :-)
Avatar of amnav

ASKER

Not clear enogh
Please post an email adres so I can send it to you
ASKER CERTIFIED SOLUTION
Avatar of Mirkwood
Mirkwood

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial