Sign in to follow this  
Followers 0
nullschritt

[Solved] Bitmap to Image Object

2 posts in this topic

#1 ·  Posted (edited)

Hello all I am working on a webcam broadcast program, and I have all the code I need but I'm having one small problem.

The data returned from the webcam is a BITMAP and I need it to be an IMAGE OBJECT, and I'm not sure how to turn the bitmap into an image object(like from _GDIPlus_ImageLoadFromFile() ) so that I can preform my resizing/compression on it. (my resizing/compression works on images loaded with _GDIPlus_ImageLoadFromFile() but doesnt seem to be able to process a regular bitmap data.)

Here's my code if it helps you understand what I want to do: (the required DLL is attached)

;--------------------------------------------------------------------------
; ESCAPI is a very simple DLL interface to use video capture devices
; (most commonly webcams, but also video in devices and other similar things)
; Get dll from --> [url="http://sol.gfxile.net/escapi/index.html"]http://sol.gfxile.net/escapi/index.html[/url]
;
#include <GDIplus.au3>
#Include <GUIConstantsEx.au3>
#Include <Memory.au3>
;--------------------------------------------------------------------------
; Local variables
Local $Width = 320 ;Escapi seems to use 640x480 (or lower) as webcam resolution and will
Local $Height = 260  ; adjust the image size to $Width by $Height
;--------------------------------------------------------------------------
; variables required for dshow escapi
Local $tagSimpleCapParams = _
"ptr mTargetBuf;" & _
"int mWidth;" & _
"int mHeight;"
Local $tSimpleCapParams = DllStructCreate($tagSimpleCapParams)
Local $tTargetBuf = DllStructCreate("BYTE[" & $Width*$Height*4 & "]")
Global $pTargetBuf = DllStructGetPtr($tTargetBuf)
DllStructSetData($tSimpleCapParams, 1, $pTargetBuf)
DllStructSetData($tSimpleCapParams, 2, $Width)
DllStructSetData($tSimpleCapParams, 3, $Height)
Local $pSimpleCapParams = DllStructGetPtr($tSimpleCapParams)
Local $device = 0 ;change this number to select dshow device
Local $sver = "--ERROR--"
Local $tCam = DllStructCreate("CHAR v[20]") ;buffer used to get ESCAPI device name
DllStructSetData($tCam, 1, $sver)
Local $pCam = DllStructGetPtr($tCam)
;---------------------------------------------------------------------------
;Escapi init and get Information
local $_escapi_Dll = DllOpen("escapi.dll")
Local $CamInfo
;ESCAPI version
$return = DllCall($_escapi_Dll,"int","ESCAPIDLLVersion")
$CamInfo &= "Dll version = " & Hex($return[0],3) & @CRLF
$return = DllCall($_escapi_Dll,"int","initCOM")
; get number of available devices
$return = DllCall($_escapi_Dll,"int","countCaptureDevices")
$CamInfo &= "Number of devices = " & $return[0] & @CRLF
; get selected device name, $device = 0
DllCall($_escapi_Dll,"none:cdecl","getCaptureDeviceName", "uint" , $device, "ptr" , $pCam  , "int" , 20)
Local $vCam = DllStructGetData($tCam , 1)
$CamInfo &= "First device name = " & $vCam & @CRLF
MsgBox(0,"ESCAPI info", $CamInfo)
$return = DllCall($_escapi_Dll,"int:cdecl","initCapture", "int", $device, "ptr", $pSimpleCapParams)
;---------------------------------------------------------------------------
; GUI and GDI init
Global $hwnd = GUICreate("EscApi WebCam", $Width, $Height)
GUISetState(@SW_SHOW,$hwnd)
_GDIPlus_Startup()
Global $hGraphics = _GDIPlus_GraphicsCreateFromHWND($hwnd)
;---------------------------------------------------------------------------
$frames = 0
While 1
Local $msg = GUIGetMsg()
If $msg = $GUI_EVENT_CLOSE Then ExitLoop
sleep(10)
DllCall($_escapi_Dll,"none:cdecl","doCapture", "int", $device)
Do
$return = DllCall($_escapi_Dll,"int:cdecl","isCaptureDone", "int", $device)
sleep(10)
Until $return[0] = 1
$hBMP = _WinAPI_CreateBitmap($Width, $Height , 1 , 32 , $pTargetBuf)
Local $hImage = _GDIPlus_BitmapCreateFromHBITMAP($hBMP)

    Local $iWidth = 300
    Local $iHeight = _GDIPlus_ImageGetHeight($hImage) * 300 / _GDIPlus_ImageGetWidth($hImage)
        Local $Widthx = 100
    Local $Heightx = _GDIPlus_ImageGetHeight($hImage) * 100 / _GDIPlus_ImageGetWidth($hImage)
$himage = _gdiplus_scaleimage2($hImage, $width, $height)
$hImage = _GDIPlus_BitmapCloneArea ( $himage, 0, 0, $widthx, $heightx,  $GDIP_PXF16RGB555 )
$file = FileOpen(@scriptdir&"\temp.jpg", 18)
FileWrite($file, _gdiplus_saveimage2binary($hImage, 50))
   FileClose($file)
 Local $hImage = _GDIPlus_ImageLoadFromFile(@scriptdir&"\temp.jpg")
$himage = _gdiplus_scaleimage2($hImage, $width, $height)
$hbitmapxx = _GDIPlus_BitmapCloneArea ( $himage, 0, 0, $width, $height,  $GDIP_PXF16RGB555 )


_GDIPlus_GraphicsDrawImageRect($hGraphics, $hbitmapxx, 0, 0, $Width, $Height)
_GDIPlus_BitmapDispose($hImage)
     _WinAPI_DeleteObject($hBMP)
     $frames += 1
     ConsoleWrite("Processed Frame: "&$frames&@CRLF)
WEnd
;--------------------------------------------------------------------------
;Clean up
$return = DllCall($_escapi_Dll,"none:cdecl","deinitCapture", "int", $device)
DllClose($_escapi_Dll)
_GDIPlus_GraphicsDispose($hGraphics)
_GDIPlus_Shutdown()
GUIDelete($hwnd)


    Func _gdiplus_scaleimage2($himage, $inewwidth, $inewheight, $ibgcolor = -986896, $bbgclear = True, $iinterpolationmode = 7)
        Local $iwidth = _gdiplus_imagegetwidth($himage)
        Local $iheight = _gdiplus_imagegetheight($himage)
        Local $iw, $ih, $f, $fratio
        If $iwidth > $iheight Then
            $f = $iwidth / $inewwidth
        Else
            $f = $iheight / $inewheight
        EndIf
        $iw = Int($iwidth / $f)
        $ih = Int($iheight / $f)
        If $iw > $inewwidth Then
            $fratio = $inewwidth / $iw
            $iw = Int($iw * $fratio)
            $ih = Int($ih * $fratio)
        ElseIf $ih > $inewheight Then
            $fratio = $inewheight / $ih
            $iw = Int($iw * $fratio)
            $ih = Int($ih * $fratio)
        EndIf
        Local $hbitmap = DllCall($__g_hGDIPDll, "uint", "GdipCreateBitmapFromScan0", "int", $iw, "int", $ih, "int", 0, "int", 2498570, "ptr", 0, "int*", 0)
        If @error Then Return SetError(3, 0, 0)
        $hbitmap = $hbitmap[6]
        Local $hbmpctxt = _gdiplus_imagegetgraphicscontext($hbitmap)
        If $bbgclear Then _gdiplus_graphicsclear($hbmpctxt, $ibgcolor)
        DllCall($__g_hGDIPDll, "uint", "GdipSetInterpolationMode", "handle", $hbmpctxt, "int", $iinterpolationmode)
        _gdiplus_graphicsdrawimagerect($hbmpctxt, $himage, 0, 0, $iw, $ih)
        _gdiplus_imagedispose($himage)
        _gdiplus_graphicsdispose($hbmpctxt)
        Return $hbitmap
    EndFunc

    Func _sendmsg($to, $msg)
    EndFunc

        Func _gdiplus_saveimage2binary($hbitmap, $iquality = 10)
        Local $simgclsid = _gdiplus_encodersgetclsid("jpg")
        Local $tguid = _winapi_guidfromstring($simgclsid)
        Local $pencoder = DllStructGetPtr($tguid)
        Local $tparams = _gdiplus_paraminit(1)
        Local $tdata = DllStructCreate("int Quality")
        DllStructSetData($tdata, "Quality", $iquality)
        Local $pdata = DllStructGetPtr($tdata)
        _gdiplus_paramadd($tparams, $gdip_epgquality, 1, $gdip_eptlong, $pdata)
        Local $pparams = DllStructGetPtr($tparams)
        Local $hstream = DllCall("ole32.dll", "uint", "CreateStreamOnHGlobal", "ptr", 0, "bool", True, "ptr*", 0)
        $hstream = $hstream[3]
        DllCall($__g_hGDIPDll, "uint", "GdipSaveImageToStream", "ptr", $hbitmap, "ptr", $hstream, "ptr", $pencoder, "ptr", $pparams)
        Local $hmemory = DllCall("ole32.dll", "uint", "GetHGlobalFromStream", "ptr", $hstream, "ptr*", 0)
        $hmemory = $hmemory[2]
        Local $imemsize = _memglobalsize($hmemory)
        Local $pmem = _memgloballock($hmemory)
        $tdata = DllStructCreate("byte[" & $imemsize & "]", $pmem)
        Local $bdata = DllStructGetData($tdata, 1)
        Local $tvariant = DllStructCreate("word vt;word r1;word r2;word r3;ptr data;ptr")
        DllCall("oleaut32.dll", "long", "DispCallFunc", "ptr", $hstream, "dword", 8 + 8 * @AutoItX64, "dword", 4, "dword", 23, "dword", 0, "ptr", 0, "ptr", 0, "ptr", DllStructGetPtr($tvariant))
        _memglobalfree($hmemory)
        Return $bdata
    EndFunc

escapi21.zip

Edited by nullschritt

Share this post


Link to post
Share on other sites



Answered my own question by using _GDIPlus_ImageLoadFromStream()

If anyone has a faster/better solution feel free to post it.

Share this post


Link to post
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!


Register a new account

Sign in

Already have an account? Sign in here.


Sign In Now
Sign in to follow this  
Followers 0