|
Post by weathermansweden on Dec 27, 2022 2:40:27 GMT 1
Hello,
I have tried export / save the graphic to a bmp-file after opening a form and then generating a graphic with D2 commands. But somehow it does not work.
Can somebody please explain to me how to save a render taget for D2 commands as a file?
Thank you.
|
|
|
Post by (X) on Dec 28, 2022 16:06:43 GMT 1
This seems to be the key to solving your dilemma. Here is a demo that lets you save a D2D render target to a bitmap in 3 modes:{Selected Area, Work Area, Bitmap Area}. You can chose the mode with a combination of Right-Click and Alt, Ctrl or Shift keys.
'################################################################################# ' ' DISCLAIMER: THIS CODE IS OFFERED AS IS FOR EDUCATIONAL PURPOSES. ' YOU ARE FREE TO USE, COPY AND DISTRIBUTE. ' THE USE OF THIS CODE IS AT YOUR OWN RISK. ' I ACCEPT NO LIABILITY NOR MAKE ANY CLAIM OF ' CORRECTNESS OR SUITABILITY IN PART OR IN WHOLE. ' '################################################################################# ' ' FILENAME Demo D2SaveBmp.G32 ' ' DESCRIPTION A work around to save a D2D render target area to a bitmap file. ' ' AUTHOR (X) ' EMAIL xman.gb32@gmail.com ' WEBSITE https://gfabasic32.blogspot.com/ ' FORUM https://gb32.proboards.com/ ' STARTED 2022-12-27 Confirmed we CAN copy render target to <form>.hDC2 with BitBlt ' UPDATED 2022-12-28 Added 3 modes to save the D2D render target. '
P_Main
Proc P_Main $ManifestOff $Library "Direct2D" $Library "GfaWinX" $Library "UpdateRT" UpdateRuntime P_Init_Globals P_Init_Forms Do Sleep Until Win_1 Is Nothing EndProc
Proc P_Init_Forms '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Create the main form: Win_1... ' OpenW 1, 0, 0, 800, 700, ~15 With Win_1 .Caption = App.Name .ToolTipText = "Right_Click + {Alt=Work | Ctrl=BMP | Shift=Select}" EndWith '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Add a status bar for a bit of feedback... ' Ocx StatusBar sb1 '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Assign the render target handle to the render target variabe: Win1RT. ' Set Win1RT = D2GetRT() '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Assign a D2D bitmap handle to the bitmap object: oBmp... ' Set oBmp = D2Bitmap(":goldfish") '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Assign the bitmap width and height to specified variables... ' D2BitmapSize oBmp, BmpW, BmpH EndProc
Proc P_Init_Globals Global Object Win1RT, oBmp Global BmpX! = 20, BmpY! = 30, BmpW!, BmpH! Global aX!, aY!, aW!, aH! Global Enum SaveWrkArea, SaveBmpArea, SaveSelArea EndProc
Sub Win_1_Click '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Respond to a right click + modifier key... ' If (MouseK == 2) // Right-Click If (MouseKB == 1) P_D2SaveBmp(SaveSelArea) // Shift If (MouseKB == 2) P_D2SaveBmp(SaveBmpArea) // Ctrl If (MouseKB == 4) P_D2SaveBmp(SaveWrkArea) // Alt EndIf EndSub
Proc P_SelectSaveArea() '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Initialize the area x and y values to the current mouse x,y position... ' aX = MouseX aY = MouseY '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Remind the user how to end the selection... ' sb1.SimpleText = "Use left-click to end selection." '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Start the rubber box selection of the area you want to save... ' RubberBox aX, aY, -_X, -_Y, aW, aH '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Adjust the area values of x, y, w and h depending on positive or negative ' results. ' If (aW < 0) aX += aW If (aH < 0) aY += aH aW = Abs(aW) aH = Abs(aH) EndProc
Proc P_D2SaveBmp(SaveOption%) Try '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Make sure the render target has been painted at least once. ' Win_1_Paint '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' There does not seem to be a way to directly save a D2D render target area to a ' bitmap file. However, one CAN copy the content of the render target area to a ' form's backbuffer and use the SavePicture command to save this area to a ' bitmap file. To assign a backbuffer to a form, we can use the AutoRedraw ' property. ' ' <form>.Autoredraw = 1 // or: 2, but, 0 does not provide a back buffer ' '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Depending on the specified save option, initialize the file name and set the ' area x, y, w and h ' Dim fn$ Select SaveOption Case SaveWrkArea fn$ = "AreaWrk" aX = 0, aY = 0, aW = Win_1.ScaleWidth, aH = Win_1.ScaleHeight Case SaveBmpArea fn$ = "AreaBmp" aX = BmpX, aY = BmpY, aW = BmpW!, aH = BmpH! Case SaveSelArea P_SelectSaveArea() °Debug aX, aY, aW, aH fn$ = "AreaSel" EndSelect '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Build a full path file name for the bitmap file. ' fn$ = App.Path & "\" & fn$ & ".Bmp" '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Let the user see what file name was used. ' sb1.SimpleText = "Saving to:" & fn$ '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Lets create a hidden temporary form to hold the transfered image, then close ' it after use. ' // Even with all properties such as .Caption disabled. // I can't get width to go below 136 pixels. Why???. °Form Hidden frmTemp = , 0, 0, aW, aH // Yes, I was able to get width to go below 136 pixels using the Form Editor! °LoadForm frmTemp Hidden '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' OCX Form width CAN be set below 136 pixels. So, I might use this in a library! ' Ocx Form frmTemp = , 0, 0, aW, aH With frmTemp .Appearance = 0 .AutoRedraw = 1 .Width = aW ' PixelsToTwipX(aW) .Height = aH ' PixelsToTwipY(aH) .BorderStyle = 0 .Caption = "" .ControlBox = False .Hide .MaxButton = False .MinButton = False .HelpButton = False Trace .Width Trace .Height EndWith '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' The following copies the render target's front source device context via this ' handle: <form>.hDC to a back destination device context via this handle: ' <form>.hDC2 ' Dim src% = Win_1.hDC Dim sx% = aX, sy% = aY Dim sw% = aW, sh% = aH Dim dst% = frmTemp.hDC2 Dim dx% = 0, dy% = 0 BitBlt src, sx, sy, sw, sh, dst, dx, dy, SRCCOPY '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Save the image of the specified form to the specified bitmap file. ' SavePicture frmTemp.Image, fn$ '''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''' ' Close temporary hidden form. ' frmTemp.Close Catch Trace Err$ EndCatch EndProc
Sub Win_1_Paint D2BeginDraw Win1RT, D2C_White D2Put BmpX, BmpY, oBmp D2EndDraw EndSub
Attachments:
Demo D2SaveBmp.G32 (59.92 KB)
|
|
|
Post by (X) on Dec 28, 2022 19:03:37 GMT 1
|
|
|
Post by weathermansweden on Dec 28, 2022 23:03:44 GMT 1
Thank you very much for your fast reply, for your explanation and the program that you provided. I am so glad that there are still other GFA-Basic users around!
|
|
|
Post by (X) on Dec 30, 2022 3:28:41 GMT 1
|
|
|
Post by (X) on Jan 1, 2023 23:04:49 GMT 1
|
|