2 Bilder übereinander legen

  • Hi,

    ist es möglich mit Autoit zwei Bilder (JPG/PNG) übereinander zu legen und dieses wieder als ein Bild zu speichern?
    Ziel ist es devierse definierte "Bilderrahmen" mit Transparenz über Digicam-Fotos zu legen, wobei dementsprechend die Transparenz unbedingt erhalten werden muss.

    Am ende soll das ganze, wenn möglich im Hintergrund, geschehen.

    Danke & Gruß

    Einmal editiert, zuletzt von hanni-nbg (24. Februar 2013 um 16:17)

  • ja, das geht mit GDIPlus und auch im Hintergrund.
    ungetestet, so ähnlich sollte es gehen :

    [autoit]

    #include<GDIPlus.au3>

    [/autoit][autoit][/autoit][autoit]

    _GDIPlus_Startup()

    [/autoit][autoit][/autoit][autoit]

    Local $hImage1 = _GDIPlus_ImageLoadFromFile("Rahmen.jpg")
    Local $hImage2 = _GDIPlus_ImageLoadFromFile("Bild.jpg")
    Local $hImage1Draw = _GDIPlus_ImageGetGraphicsContext($hImage1)

    [/autoit][autoit][/autoit][autoit]

    _GDIPlus_GraphicsDrawImage($hImage1Draw, $hImage2, 0, 0)
    _GDIPlus_ImageSaveToFile($hImage1,"Fertiges Bild.png")

    [/autoit][autoit][/autoit][autoit]

    _GDIPlus_ImageDispose($hImage1)
    _GDIPlus_ImageDispose($hImage2)
    _GDIPlus_GraphicsDispose($hImage1Draw)
    _GDIPlus_Shutdown()

    [/autoit]

    3 Mal editiert, zuletzt von Alcros (22. Februar 2013 um 18:05)

  • Das sollte ungefähr deinen Vorstellungen entsprechen, muss aber wahrscheinlich noch angepasst/ausgebaut werden.

    Spoiler anzeigen
    [autoit]

    #include <GDIPlus.au3>

    [/autoit] [autoit][/autoit] [autoit]

    $sPath_PicBG = FileOpenDialog("Select Background Picture", "", "JPG (*.jpg;*.jpeg)")
    If @error Then Exit
    $sPath_PicFrame = FileOpenDialog("Select Frame Picture", "", "PNG (*.png)")
    If @error Then Exit
    $sPath_Save = FileSaveDialog("Save Path", "", "JPG (*.jpg;*.jpeg)")
    If @error Then Exit

    [/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_Startup()

    [/autoit] [autoit][/autoit] [autoit]

    $hImage_BG = _GDIPlus_ImageLoadFromFile($sPath_PicBG)
    $hImage_Frame = _GDIPlus_ImageLoadFromFile($sPath_PicFrame)

    [/autoit] [autoit][/autoit] [autoit]

    $iWidth = _GDIPlus_ImageGetWidth($hImage_BG)
    $iHeight = _GDIPlus_ImageGetHeight($hImage_BG)

    [/autoit] [autoit][/autoit] [autoit]

    $hGraphics = _GDIPlus_ImageGetGraphicsContext($hImage_BG)

    [/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_GraphicsDrawImageRect($hGraphics, $hImage_Frame, 0, 0, $iWidth, $iHeight)

    [/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_ImageSaveToFile($hImage_BG, $sPath_Save)

    [/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_GraphicsDispose($hGraphics)
    _GDIPlus_ImageDispose($hImage_BG)
    _GDIPlus_ImageDispose($hImage_Frame)
    _GDIPlus_Shutdown()

    [/autoit]

    Edit: Da war jemand schneller :P... Meine Version streckt den Rahmen über das ganze Bild, die von Alcros orientiert sich an der Größe des Rahmens. Wenn dein Rahmen genau die selben Ausmaße hat wie das Bild, dann macht es keinen Unterschied was du benutzt. ;)

  • was ist eigentlich der genaue Unterschied zwischen

    [autoit]

    _GDIPlus_BitmapCreateFromFile
    _GDIPlus_ImageLoadFromFile

    [/autoit]


    ?
    Bei meinen bisherigen Projekten funktioniert beides

  • Hi Alcros,

    eigentlich ist es doch egal in welchem Format das Bild am ende gespeichert wird, solange die Bilder beim übereinanderlegen Ihre Transparenz behalten oder?
    Ich hab mir das so vorgestellt
    [PNG Rahmen Transparent] -> [JPG nicht transparent] ergibt ein Bild bei dem das PNG durchscheint. Und dann kann man es ja wieder als JPG speichern oder?

  • Vielen Dank erst mal an euch beide.
    habe das ganze nun getestet, komme aber nicht zu einem 100%igem Ergebnis.

    Mit folgendem Quelltext:

    [autoit]

    #include<GDIPlus.au3>

    [/autoit][autoit][/autoit][autoit]

    _GDIPlus_Startup()

    [/autoit][autoit][/autoit][autoit][/autoit][autoit]

    Local $hImage1 = _GDIPlus_BitmapCreateFromFile("C:\Users\Johannes\Downloads\CAMPHOTOS\IMG_1612.JPG")
    Local $hImage2 = _GDIPlus_BitmapCreateFromFile("C:\Users\Johannes\Downloads\fotokabine_v0.3\images\frame.png")
    Local $hImage1Draw = _GDIPlus_ImageGetGraphicsContext($hImage1)

    [/autoit][autoit][/autoit][autoit]

    _GDIPlus_GraphicsDrawImage($hImage1Draw, $hImage2, 0, 0)
    _GDIPlus_ImageSaveToFile($hImage1,"C:\Users\user\Downloads\CAMPHOTOS\Fertiges Bild.png")

    [/autoit][autoit][/autoit][autoit]

    _GDIPlus_BitmapDispose($hImage1)
    _GDIPlus_BitmapDispose($hImage2)
    _GDIPlus_GraphicsDispose($hImage1Draw)
    _GDIPlus_Shutdown()

    [/autoit]

    Erhalte ich Ergebnis Fertiges Bild 1.png (Bild OK, Rahmen viel zu groß)

    Drehe ich das png und das jpg um erhalte ich das Ergebnis Fertiges Bild 2.png (Rahmen OK, Bild zu klein und Bild über Rahmen)
    Kann ich nicht noch irgendwo eine Skalierung und oder eine größe angeben? Sowohl Rahmen als auch Bild sind beide definitiv 1600x1200 Px groß.

    Stehe mit GDIPlus gerade wirklich noch auf Kriegsfuss.

    Danke!

    PS: Habe die angehängten Bilder aufgrund der Größenbeschränkung verkleinert

  • Danke name22,

    hat super geklappt.

    Eine Frage noch.
    Wäre es auch möglich ein drittes Bild mit ins Spiel zu bringen (auf jeder Seite 100px größer als der background und der Rahmen) und auf dieses dann den Background und den Rahmen mittig um beispielsweise 10° gedreht zu platzieren?

    Danke!

  • Das ist etwas aufwändiger. Zumindest für die Drehung der Bilder benötigst du eine Matrix, der Rest ist simpel.
    Wenn ich dich richtig verstanden habe, dann sollte das hier funktionieren:

    Spoiler anzeigen
    [autoit]

    #include <GDIPlus.au3>

    [/autoit] [autoit][/autoit] [autoit]

    $sPath_PicBG = FileOpenDialog("Select Background Picture", "", "JPG (*.jpg;*.jpeg)")
    If @error Then Exit
    $sPath_PicOver = FileOpenDialog("Select Overlay Picture", "", "JPG (*.jpg;*.jpeg)")
    If @error Then Exit
    $sPath_PicFrame = FileOpenDialog("Select Frame Picture", "", "PNG (*.png)")
    If @error Then Exit
    $sPath_Save = FileSaveDialog("Save Path", "", "JPG (*.jpg;*.jpeg)")
    If @error Then Exit
    $iAngle = InputBox("Angle", "Picture Angle (Degree):", 0, Default, 200, 120)

    [/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_Startup()

    [/autoit] [autoit][/autoit] [autoit]

    $hImage_BG = _GDIPlus_ImageLoadFromFile($sPath_PicBG)
    $hImage_Over = _GDIPlus_ImageLoadFromFile($sPath_PicOver)
    $hImage_Frame = _GDIPlus_ImageLoadFromFile($sPath_PicFrame)

    [/autoit] [autoit][/autoit] [autoit]

    $aDim_BG = _GDIPlus_ImageGetDimension($hImage_BG)
    $aDim_Over = _GDIPlus_ImageGetDimension($hImage_Over)
    $aDim_Frame = _GDIPlus_ImageGetDimension($hImage_Frame)

    [/autoit] [autoit][/autoit] [autoit]

    $hGraphics = _GDIPlus_ImageGetGraphicsContext($hImage_BG)
    _GDIPlus_GraphicsSetSmoothingMode($hGraphics, 2)

    [/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_GraphicsTranslateTransform($hGraphics, $aDim_BG[0] / 2, $aDim_BG[1] / 2)
    _GDIPlus_GraphicsRotateTransform($hGraphics, $iAngle)
    _GDIPlus_GraphicsTranslateTransform($hGraphics, -$aDim_BG[0] / 2, -$aDim_BG[1] / 2)
    _GDIPlus_GraphicsDrawImageRect($hGraphics, $hImage_Over, $aDim_BG[0] / 2 - $aDim_Over[0] / 2, $aDim_BG[1] / 2 - $aDim_Over[1] / 2, $aDim_Over[0], $aDim_Over[1])
    _GDIPlus_GraphicsDrawImageRect($hGraphics, $hImage_Frame, $aDim_BG[0] / 2 - $aDim_Over[0] / 2, $aDim_BG[1] / 2 - $aDim_Over[1] / 2, $aDim_Over[0], $aDim_Over[1])

    [/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_ImageSaveToFile($hImage_BG, $sPath_Save)

    [/autoit] [autoit][/autoit] [autoit]

    _GDIPlus_GraphicsDispose($hGraphics)
    _GDIPlus_ImageDispose($hImage_BG)
    _GDIPlus_ImageDispose($hImage_Over)
    _GDIPlus_ImageDispose($hImage_Frame)
    _GDIPlus_Shutdown()

    [/autoit] [autoit][/autoit] [autoit][/autoit] [autoit]

    #region GDIP.au3
    ; #FUNCTION# ====================================================================================================================
    ; Name...........: _GDIPlus_ImageGetDimension
    ; Description ...: Gets the width and height of an image
    ; Syntax.........: _GDIPlus_ImageGetDimension($hImage)
    ; Parameters ....: $hImage - Pointer to an Image object
    ; Return values .: Success - Array that contains the rectangle coordinates and dimensions:
    ; |[0] - Width of the image
    ; |[1] - Height of the image
    ; Failure - -1 and either:
    ; |@error and @extended are set if DllCall failed
    ; |$GDIP_STATUS contains a non zero value specifying the error code
    ; Remarks .......: None
    ; Related .......: None
    ; Link ..........; @@MsdnLink@@ GdipGetImageDimension
    ; Example .......; No
    ; ===============================================================================================================================
    Func _GDIPlus_ImageGetDimension($hImage)
    Local $aSize[2], $aResult

    [/autoit] [autoit][/autoit] [autoit]

    $aResult = DllCall($ghGDIPDll, "uint", "GdipGetImageDimension", "hwnd", $hImage, "float*", 0, "float*", 0)
    If @error Then Return SetError(@error, @extended, -1)

    [/autoit] [autoit][/autoit] [autoit]

    $GDIP_STATUS = $aResult[0]
    If $GDIP_STATUS Then Return -1

    [/autoit] [autoit][/autoit] [autoit]

    $aSize[0] = $aResult[2]
    $aSize[1] = $aResult[3]
    Return $aSize
    EndFunc ;==>_GDIPlus_ImageGetDimension

    [/autoit] [autoit][/autoit] [autoit]

    ; #FUNCTION# ====================================================================================================================
    ; Name...........: _GDIPlus_GraphicsTranslateTransform
    ; Description ...: Updates a Graphics object's world transformation matrix with the product of itself and a translation matrix
    ; Syntax.........: _GDIPlus_GraphicsTranslateTransform($hGraphics, $nDX, $nDY[, $iOrder = 0])
    ; Parameters ....: $hGraphics - Pointer to a Graphics object
    ; $nDX - Horizontal component of the translation
    ; $nDY - Vertical component of the translation
    ; $iOrder - Order of matrices multiplication:
    ; |0 - The translation matrix is on the left
    ; |1 - The translation matrix is on the right
    ; Return values .: Success - True
    ; Failure - False and either:
    ; |@error and @extended are set if DllCall failed
    ; |$GDIP_STATUS contains a non zero value specifying the error code
    ; Remarks .......: None
    ; Related .......: None
    ; Link ..........; @@MsdnLink@@ GdipTranslateWorldTransform
    ; Example .......; No
    ; ===============================================================================================================================
    Func _GDIPlus_GraphicsTranslateTransform($hGraphics, $nDX, $nDY, $iOrder = 0)
    Local $aResult = DllCall($ghGDIPDll, "uint", "GdipTranslateWorldTransform", "hwnd", $hGraphics, "float", $nDX, "float", $nDY, "int", $iOrder)

    [/autoit] [autoit][/autoit] [autoit]

    If @error Then Return SetError(@error, @extended, False)
    $GDIP_STATUS = $aResult[0]
    Return $aResult[0] = 0
    EndFunc ;==>_GDIPlus_GraphicsTranslateTransform

    [/autoit] [autoit][/autoit] [autoit]

    ; #FUNCTION# ====================================================================================================================
    ; Name...........: _GDIPlus_GraphicsRotateTransform
    ; Description ...: Updates the world transformation matrix of a Graphics object with the product of itself and a rotation matrix
    ; Syntax.........: _GDIPlus_GraphicsRotateTransform($hGraphics, $nAngle[, $iOrder = 0])
    ; Parameters ....: $hGraphics - Pointer to a Graphics object
    ; $nAngle - The angle, in degrees, of rotation
    ; $iOrder - Order of matrices multiplication:
    ; |0 - The rotation matrix is on the left
    ; |1 - The rotation matrix is on the right
    ; Return values .: Success - True
    ; Failure - False and either:
    ; |@error and @extended are set if DllCall failed
    ; |$GDIP_STATUS contains a non zero value specifying the error code
    ; Remarks .......: None
    ; Related .......: _GDIPlus_GraphicsMultiplyTransform
    ; Link ..........; @@MsdnLink@@ GdipRotateWorldTransform
    ; Example .......; No
    ; ===============================================================================================================================
    Func _GDIPlus_GraphicsRotateTransform($hGraphics, $nAngle, $iOrder = 0)
    Local $aResult = DllCall($ghGDIPDll, "uint", "GdipRotateWorldTransform", "hwnd", $hGraphics, "float", $nAngle, "int", $iOrder)

    [/autoit] [autoit][/autoit] [autoit]

    If @error Then Return SetError(@error, @extended, False)
    $GDIP_STATUS = $aResult[0]
    Return $aResult[0] = 0
    EndFunc ;==>_GDIPlus_GraphicsRotateTransform
    #endregion

    [/autoit]
  • Hi name22,

    danke, werde das testen.

    Ist beim Ausführen des vorrherigen Skripts in einer Schleife was zu beachten?
    Ich erhalte nach dem ersten Schleifendurchlauf immer die Fehlermeldung

    [autoit]

    :\Program Files (x86)\AutoIt3\Include\GDIPlus.au3 (957) : ==> Subscript used with non-Array variable.:
    For $iI = 1 To $aEncoders[0][0]
    For $iI = 1 To $aEncoders^ ERROR

    [/autoit]

    Anbei der Quelltext

    [autoit]

    for $i = 1 to $pic_array[0]
    $hImage_BG = _GDIPlus_ImageLoadFromFile($pic_path & $pic_array[$i])
    $hImage_Frame = _GDIPlus_ImageLoadFromFile($bg_images & "frame.png")

    [/autoit][autoit][/autoit][autoit]

    $iWidth = _GDIPlus_ImageGetWidth($hImage_BG)
    $iHeight = _GDIPlus_ImageGetHeight($hImage_BG)

    [/autoit][autoit][/autoit][autoit]

    $hGraphics = _GDIPlus_ImageGetGraphicsContext($hImage_BG)
    msgbox(0,"","gdpiplus")
    _GDIPlus_GraphicsDrawImageRect($hGraphics, $hImage_Frame, 0, 0, $iWidth, $iHeight)
    msgbox(0,"",$pic_path & "transform_" & $pic_array[$i])
    _GDIPlus_ImageSaveToFile($hImage_BG, $pic_path & "transform_" & $pic_array[$i])
    msgbox(0,"","gdiplus2")
    _GDIPlus_GraphicsDispose($hGraphics)
    _GDIPlus_ImageDispose($hImage_BG)
    _GDIPlus_ImageDispose($hImage_Frame)
    _GDIPlus_Shutdown()
    Next

    [/autoit]

    In $pic_array stehen die Bildernamen (IMG_XXXX.JPG usw)
    In $pic_path der aktuelle Bilderpfad (C:\users\...)

    Beim ersten Durchlauf erhalte ich alle drei Message Boxes und es wird ein Bild mit Rahmen erstellt.
    Beim zweiten Durchlauf komme ich auch bis zur dritten Message Box und danach erhalte ich die Fehlermeldung.

    Gibts da was spezifisches bei GDIPlus im zusammenhang mit ner Schleife zu beachten?

    Vielen Dank!