Seite 1 von 2
Bild per API laden und kopieren
Verfasst: 19.04.2021 16:14
von jacdelad
Hallo,
ich will ein Bild per Windows API laden und dann weiterverarbeiten. Hintergrund ist mein RibbonGadget, das auch als DLL für XProfan bereit stehen soll. Das Bild wird in dem Fall vom XProfan-Programm geladen und an die DLL übergeben. Das hat auch erst funktioniert, jetzt habe ich aber eine ganze Menge geändert und plötzlich klappt es nicht mehr. ich habe meine Backups durchgesehen und konnte an den Stellen, die ich für entscheidend halte, keine Unterschiede feststellen.
Lange Rede, kurzer Sinn: Das Problem ist, dass GetObject_() immer 0 zurückgibt, also fehlschlägt. Deshalb kann das (für die DLL externe) Bild nicht weiterverwendet werden. In der DLL sollen Eigenschaften wie Breite und Höhe per GetObject_() ausgelesen werden (wie gesagt, das schlägt fehl). Mein Ablauf ist in etwa
Bild -> GetObject_() -> StartDrawing() auf Zielbild -> DrawImage() auf Zielbild (ImageID vom Quellbild entfällt, weil es ja ein Handle und keine ID ist).
Jetzt habe ich ein minimales Beispiel geschrieben. Mit Bitmaps funktioniert GetObject, mit Icons aber nicht:
Code: Alles auswählen
image=LoadImage_(GetModuleHandle_(0),"D:\PureBasic\Ribbon\Icon1.ico",#IMAGE_ICON,1080,1080,#LR_LOADFROMFILE)
Debug image
Debug GetObject_(image,SizeOf(bitmap),@bm.bitmap)
Bin ich hier überhaupt auf dem richtigen Weg? Wie gesagt, die DLL ging erst, jetzt aber plötzlich nicht mehr.
Nochmal zusammengefasst: Das aufrufende Programm übergibt das Handle eines Bildes (erzeugt mit LoadImage_()) an die DLL. Die soll das Bild in ein neues Bild, das mit PureBasic-Befehlen erstellt wurde, kopiert werden.
Kann mir da jemand helfen?
Re: Bild per API laden und kopieren
Verfasst: 19.04.2021 17:57
von Mijikai
Ich nutze GetObject_() oft für die Bildmanipulation da es viel einfacher ist als jedesmal Start & StopDrawing aufzurufen
um and die Bits und andere Informationen zu kommen.
jacdelad hat geschrieben: 19.04.2021 16:14
Code: Alles auswählen
image=LoadImage_(GetModuleHandle_(0),"D:\PureBasic\Ribbon\Icon1.ico",#IMAGE_ICON,1080,1080,#LR_LOADFROMFILE)
Debug image
Debug GetObject_(image,SizeOf(bitmap),@bm.bitmap)
Der Beispielcode könnte so problematisch sein da GetModuleHandle_() zu hohe Werte ausgeben kann,
zudem ist es nicht klar ob der Returncode hier immer das Icon Handle ist.
Besser #PB_Any verwenden (oder eine definierte Nummer).
Mit Icons kenne ich mich nicht gut aus aber ich glaube das Icons nur Container sind die mehreren Einzelbildern enthalten können.
Evtl. reicht GetIconInfo_(), müsste mal bei MSDN schauen ob es da mehr Infos oder Limitationen gibt.
Beispiel mit GetIconInfo_()
Code: Alles auswählen
EnableExplicit
Procedure.i Main()
Protected img.i
Protected ico.ICONINFO
Protected bm.BITMAP
img = LoadImage(#PB_Any,"OneDrive.ico");<- icon einer nutzlosen windows spyware app als beispiel
If IsImage(img)
If GetIconInfo_(ImageID(img),@ico);<- container 'öffnen'
If GetObject_(ico\hbmColor,SizeOf(BITMAP),@bm);<- bitmap info mit handle holen
Debug bm\bmWidth
Debug bm\bmHeight
EndIf
EndIf
FreeImage(img)
EndIf
ProcedureReturn
EndProcedure
Main()
End
Re: Bild per API laden und kopieren
Verfasst: 19.04.2021 18:29
von jacdelad
#PB_Any kann ich nicht nehmen, weil es keine PureBasic-eigene Funktion ist.
Das Icon war auch nur ein Beispiel. In XProfan nutze ich die eingebauten Funktionen. Ich gab gerade gesehen, dass das Problem wohl doch an XProfan liegt. Bilder gehen, Icons nicht...
Re: Bild per API laden und kopieren
Verfasst: 19.04.2021 19:02
von Mijikai
jacdelad hat geschrieben: 19.04.2021 18:29
#PB_Any kann ich nicht nehmen, weil es keine PureBasic-eigene Funktion ist.
...
? #PB_Any ist nur ein Parameter, intern wird immer die jeweilige OS Api (Lib/System) verwendet.
Die Nummer Variante ist nur eine unnötige zusätzliche Verschachtelung aus Kompatibilitätsgründen (Syntax Historie).
Re: Bild per API laden und kopieren
Verfasst: 19.04.2021 19:04
von jacdelad
...aber die Funktion ist ein Windows-API-Aufruf. Windows sieht kein #PB_Any vor.
Re: Bild per API laden und kopieren
Verfasst: 19.04.2021 19:10
von Mijikai
Ich dachte LoadImage(#PB_Any,..) war gemeint (Änderung in meinem Beispiel).
Re: Bild per API laden und kopieren
Verfasst: 19.04.2021 19:16
von jacdelad
Nee, ich meine explizit LoadImage_().
Wie gesagt, mit Bildern geht's jetzt, aber mit Icons noch nicht. GetObject_() scheitert immer beim Icon.
Re: Bild per API laden und kopieren
Verfasst: 19.04.2021 20:32
von Mijikai
jacdelad hat geschrieben: 19.04.2021 19:04
...aber die Funktion ist ein Windows-API-Aufruf. Windows sieht kein #PB_Any vor.
jacdelad hat geschrieben: 19.04.2021 19:16
Nee, ich meine explizit LoadImage_().
Wie gesagt, mit Bildern geht's jetzt, aber mit Icons noch nicht. GetObject_() scheitert immer beim Icon.

LoadImage() ist aber keine Windows API sonder die PB Wrapper Funktion für die OS Api... #PB_Any ist irrelevant zum Problem.
GetModuleHandle_() kann aber ein zusätzliches Problem werden wie schon beschrieben.
Geht mein Beispiel nicht oder liegt as an XProfan... ???
Hier nochmal der GetIconInfo_() Versuch als Funktion (Image.i = #Image )
Code: Alles auswählen
Procedure.i GeWindowsImageHandle(Image.i)
Protected ico.ICONINFO
If IsImage(Image)
If GetIconInfo_(ImageID(Image),@ico)
ProcedureReturn ico\hbmColor
Else
ProcedureReturn ImageID(Image)
EndIf
EndIf
ProcedureReturn #Null
EndProcedure
GetIconInfo_() ist die Funktion die ich kenne aber am besten nochmal bei MSDN
nachlesen ob das für den Anwendungsfall ausreichend ist (Stichwort Multi-Image Icons).
Re: Bild per API laden und kopieren
Verfasst: 19.04.2021 20:46
von jacdelad
Junge!
Das Bild stammt vom aufrufenden Programm. Das ist nicht in PureBasic geschrieben, also kann es auch keine PureBasic-Funktionen nutzen. Deshalb die DLL. Es nutzt LoadImage_(), also um ehrlich zu sein nutzt es ~LoadImage(...), das Pendant von PureBasic ist LoadImage_(). Mit Unterstrich. Weil API-Aufruf. Und nein, ich kann nicht die interne Funktion nutzen. Weil das aufrufende Programm nicht in PureBasic geschrieben ist.
Re: Bild per API laden und kopieren
Verfasst: 19.04.2021 20:49
von Mijikai
jacdelad hat geschrieben: 19.04.2021 20:46
Junge!
Das Bild stammt vom aufrufenden Programm. Das ist nicht in PureBasic geschrieben, also kann es auch keine PureBasic-Funktionen nutzen. Deshalb die DLL. Es nutzt LoadImage_(), also um ehrlich zu sein nutzt es ~LoadImage(...), das Pendant von PureBasic ist LoadImage_(). Mit Unterstrich. Weil API-Aufruf. Und nein, ich kann nicht die interne Funktion nutzen. Weil das aufrufende Programm nicht in PureBasic geschrieben ist.
...GetIconInfo_() is eine OS API Funktion ImageID ist hIcon...
Code: Alles auswählen
Procedure.i GetBitmap(Handle.i,*Bitmap);<- in DLL
Protected ico.ICONINFO
If GetIconInfo_(Handle,@ico)
Handle = ico\hbmColor
EndIf
ProcedureReturn GetObject_(Handle,SizeOf(BITMAP),*Bitmap)
EndProcedure
Ich gebs auf...