Pixel Manipulation (Bits String)

Category: Bitmaps

Date: 02-16-2022

Return to Index


 
'PowerBASIC allows copying a bitmap from a graphic target to a dynamic string,
'making it relatively easy to manipulate pixels without resorting to slower commands
'such as Set Pixel.
 
'The string format is a series of 4-bytes:  w, h, clr, clr, clr, ...
'The clr values start with the top-left, 2nd Pixel of 1st row, ...
 
'Supporting functions:
   CVL to convert 4-byte String to numeric
   Mkl$ to convert numeric to 4-byte String
 
'CVL returns a number corresponding to a binary pattern stored in a string value
'MKL is the complementary function to CVL.
 
'CVL allows retrieving values beyond the first byte of the Input String variable,
'where offset indicates at what position in the string the function should start
'to retrieve a value.
Value& = CVL(x$, 3)"     'extracts the 3rd through 6th bytes of x$ and converts
                         'these 4 bytes to the corresponding Long-integer value
sReturn$ = MKL(Value&)   'returns string equivalent to binary pattern of Value&
 
'PowerBASIC suggests working with pointers to achieve the highest speed.
 
'API functions that work with DIBs require that colors be specified in BGR instead
'of the normal RGB sequence. Graphic Get Bits uses BGR format.  The BGR() function
'can translate an RGB value to its BGR equivalent.
 
'Primary Code:
'getting the string, returning the string to the graphic target
Graphic Get Bits TO bitvar$      'return a string copy of BitMap
Graphic Set Bits                 'sets graphic target to bitmap found in the string
'get w,h dimensions
xsize& = CVL(bmp$,1)
ysize& = CVL(bmp$,5)
PixelN = CVL(bmp$, n*4+8)
 
'Compilable Example:  (Jose Includes)
'The first button pops up the image dimensions
#Compiler PBWin 9, PBWin 10
#Compile EXE
#Dim All
%Unicode=1
#Include "Win32API.inc"
#Resource "gbsnippets.pbr"
Global hDlg as DWord
 
Function PBMain() As Long
   Dialog New Pixels, 0, "Test Code",300,300,200,250, %WS_OverlappedWindow To hDlg
   Control Add Button, hDlg, 100,"Get Size", 20,10,160,20
   Control Add Button, hDlg, 300,"White to Blue (pointers)", 20,40,160,20
   Control Add Button, hDlg, 400,"Blue to White (no pointers)", 20,70,160,20
   Control Add Graphic, hDlg, 200,"", 50,100,100,100   ', %ws_border
   Graphic Attach hDlg, 200
   Graphic Render "about", (0,0) - (99,99)   'Image from resource file
   Dialog Show Modal hDlg Call DlgProc
End Function
 
CallBack Function DlgProc() As Long
   Local x as long, y as long, bmp$, iColor as Long
   Local PixelPtr As Long PTR, i&
   If CB.Msg = %WM_Command AND CB.Ctl = 100 AND CB.Ctlmsg = %BN_Clicked Then
      'get w,h dimensions
      Graphic Get Bits TO bmp$      'return a string copy of BitMap
      x = CVL(bmp$,1) : y = CVL(bmp$,5)
      MsgBox Str$(x) + ":" + Str$(y)
   End If
 
   If CB.Msg = %WM_Command AND CB.Ctl = 300 AND CB.Ctlmsg = %BN_Clicked Then
      ' Change all red pixels to blue - Pointer method
      Graphic Get Bits To bmp$
      x = CVL(bmp$,1) : y = CVL(bmp$,5)
      PixelPtr = StrPTR(bmp$) + 8
      For i& = 1 To x * y
         If @PixelPtr = Bgr(%White) Then @PixelPtr = Bgr(%Blue)
         Incr PixelPtr
      Next
      Graphic Set Bits bmp$
   End If
 
   If CB.Msg = %WM_Command AND CB.Ctl = 400 AND CB.Ctlmsg = %BN_Clicked Then
      ' Change all white pixels to blue
      Graphic Get Bits To bmp$
      For i& = 9 To Len(bmp$) Step 4
         If CVL(bmp$,i&) = Bgr(%Blue) Then Mid$(bmp$,i&,4) = Mkl$(Bgr(%White))
      Next
      Graphic Set Bits bmp$
   End If
 
End Function
 
'gbs_00178
'Date: 03-10-2012


created by gbSnippets
http://www.garybeene.com/sw/gbsnippets.htm