Live-Forum - Die aktuellen Beiträge
Datum
Titel
24.04.2024 19:29:30
24.04.2024 18:49:56
Anzeige
Archiv - Navigation
1852to1856
Aktuelles Verzeichnis
Verzeichnis Index
Übersicht Verzeichnisse
Vorheriger Thread
Rückwärts Blättern
Nächster Thread
Vorwärts blättern
Anzeige
HERBERS
Excel-Forum (Archiv)
20+ Jahre Excel-Kompetenz: Von Anwendern, für Anwender
Inhaltsverzeichnis

VBA XLS AutoChange Desktop Image

VBA XLS AutoChange Desktop Image
21.10.2021 07:38:06
Dome
Hi Leute,
Da ich sehr regelmässig aktuelle Zahlen/Fakten zur Hand haben muss, nutze ich unten stehenden Code um mir ebendiese als Bild auf den Desktop zu holen. Mit Click auf einen Button werden die Zahlen auf dem Desktop dann jeweils aktualisiert.
Nun habe ich beim letztmaligen Öffnen der Datei (haben kürzlich auf Office 365 umgestellt) folgende Meldung erhalten:

Fehler beim Kompilieren: Der Code in diesem Projekt muss für die Verwendung von 64-Bit-Systemen aktualisiert werden. Überarbeiten und aktualisieren Sie Declare-Anweisungen und markieren Sie sie mit dem PtrSafe-Attribut.
Kann mir da jemand weiterhelfen?

'Quelle:
'http://www.office-loesung.de/ftopic662414_0_0_asc.php
Option Explicit
Option Private Module
Private Declare Function SystemParametersInfoA Lib "user32.dll" ( _
ByVal uAction As Long, _
ByVal uParam As Long, _
ByVal lpvParam As Any, _
ByVal fuWinIni As Long) As Long
Private Declare Function OleCreatePictureIndirect Lib "olepro32.dll" ( _
ByRef PicDesc As PIC_DESC, _
ByRef RefIID As GUID, _
ByVal fPictureOwnsHandle As Long, _
ByRef IPic As IPictureDisp) As Long
Private Declare Function CopyImage Lib "user32.dll" ( _
ByVal handle As Long, _
ByVal un1 As Long, _
ByVal n1 As Long, _
ByVal n2 As Long, _
ByVal un2 As Long) As Long
Private Declare Function IsClipboardFormatAvailable Lib "user32.dll" ( _
ByVal wFormat As Integer) As Long
Private Declare Function OpenClipboard Lib "user32.dll" ( _
ByVal hWnd As Long) As Long
Private Declare Function GetClipboardData Lib "user32.dll" ( _
ByVal wFormat As Integer) As Long
Private Declare Function DeleteObject Lib "gdi32.dll" ( _
ByVal hObject As Long) As Long
Private Declare Function CLSIDFromString Lib "ole32.dll" ( _
ByVal lpsz As Any, _
ByRef pCLSID As GUID) As Long
Private Declare Function EmptyClipboard Lib "user32.dll" () As Long
Private Declare Function CloseClipboard Lib "user32.dll" () As Long
Private Type GUID
Data1 As Long
Data2 As Integer
Data3 As Integer
Data4(0 To 7) As Byte
End Type
Private Type PIC_DESC
lngSize As Long
lngType As Long
lnghPic As Long
lnghPal As Long
End Type
Private Const PICTYPE_BITMAP As Long = 1
Private Const CF_BITMAP As Long = 2
Private Const IMAGE_BITMAP As Long = 0
Private Const LR_COPYRETURNORG  As Long = &H4
Private Const SPI_SETDESKWALLPAPER As Long = 20
Private Const SPIF_SENDWININICHANGE As Long = &H2
Private Const GUID_IPICTUREDISP As String = "{7BF80981-BF32-101A-8BBB-00AA00300CAB}"
Private llngCopy As Long
Private Function Paste_Picture() As IPictureDisp
Dim lngReturn As Long, lngPointer As Long
If CBool(IsClipboardFormatAvailable(CF_BITMAP)) Then
lngReturn = OpenClipboard(Application.Hwnd)
If lngReturn > 0 Then
lngPointer = GetClipboardData(CF_BITMAP)
llngCopy = CopyImage(lngPointer, _
IMAGE_BITMAP, 0, 0, LR_COPYRETURNORG)
Call CloseClipboard
If lngPointer  0 Then Set Paste_Picture = _
Create_Picture(llngCopy, 0&, CF_BITMAP)
End If
End If
End Function
Private Function Create_Picture( _
ByVal lnghPic As Long, _
ByVal lnghPal As Long, _
ByVal lngPicType As Long) As IPictureDisp
Dim udtPicInfo As PIC_DESC, udtID_IDispatch As GUID
Dim objPicture As IPictureDisp
Call CLSIDFromString(StrPtr( _
GUID_IPICTUREDISP), udtID_IDispatch)
With udtPicInfo
.lngSize = Len(udtPicInfo)
.lngType = PICTYPE_BITMAP
.lnghPic = lnghPic
.lnghPal = lnghPal
End With
Call OleCreatePictureIndirect(udtPicInfo, _
udtID_IDispatch, 0&, objPicture)
Set Create_Picture = objPicture
Set objPicture = Nothing
End Function
Public Sub Desk_Images()
Call CreateDesktopPicture("Desktop_NAME", Tabelle1.Range("A4:F30"), True)
End Sub
Private Sub CreateDesktopPicture(ByVal pvstrFileName As String, _
ByRef probjRange As Range, ByVal pvblnShowOnDesktop As Boolean)
Dim strFirstFileName As String, strSecondFileName As String
Dim objPicture As IPictureDisp
Dim objImageFile As Object
Dim objImageProcess As Object
Call OpenClipboard(Application.Hwnd)
Call EmptyClipboard
Call CloseClipboard
On Error Resume Next
Do
DoEvents
Call probjRange.CopyPicture(Appearance:=xlScreen, Format:=xlBitmap)
If Err.Number = 0 Then Exit Do
Call Err.Clear
Loop
On Error GoTo 0
Set objPicture = Paste_Picture()
If Not objPicture Is Nothing Then
strFirstFileName = Environ$("TMP") & "\TMP.bmp"
Call SavePicture(Picture:=objPicture, Filename:=strFirstFileName)
strSecondFileName = "Beispiel-URL" & "\" & pvstrFileName & ".bmp"
If Dir$(PathName:=strSecondFileName)  vbNullString Then _
Call Kill(PathName:=strSecondFileName)
Set objImageFile = CreateObject(Class:="WIA.ImageFile")
Set objImageProcess = CreateObject(Class:="WIA.ImageProcess")
Call objImageFile.LoadFile(Filename:=strFirstFileName)
Call objImageProcess.Filters.Add(FilterID:=objImageProcess.FilterInfos("Crop").FilterID)
With objImageProcess.Filters(1)
.Properties("Top") = 1
.Properties("Bottom") = 0
.Properties("Left") = 1
.Properties("Right") = 0
End With
Set objImageFile = objImageProcess.Apply(Source:=objImageFile)
Call objImageFile.SaveFile(Filename:=strSecondFileName)
Set objImageFile = Nothing
Set objImageProcess = Nothing
If pvblnShowOnDesktop Then Call SystemParametersInfoA(SPI_SETDESKWALLPAPER, _
0&, strSecondFileName, SPIF_SENDWININICHANGE)
Call Kill(PathName:=strFirstFileName)
Else
MsgBox "Error - table can't show on desktop", vbCritical, "Error"
End If
Call DeleteObject(llngCopy)
End Sub
Herzlichen Dank für Eure Gedanken dazu.
Beste Grüsse
Dome

3
Beiträge zum Forumthread
Beiträge zu diesem Forumthread

Betreff
Datum
Anwender
Anzeige
AW: VBA XLS AutoChange Desktop Image
21.10.2021 07:50:37
Dome
Hi Leute,
Hab das mit ptrSafe lösen können und die Declare-Anweisung ergänzt, jetzt kommt aber ein Laufzeitfehler 53, dass die Datei olepro32.dll nicht gefunden werden kann.
Besten Dank für ein Feedback.
Gruss
Dome
AW: VBA XLS AutoChange Desktop Image
21.10.2021 08:48:57
Nepumuk
Hallo,
nur PtrSafe einzusetzen genügt nicht. Da sind auch Deklarationen zu ändern. Und im 64Bit Office gibt es die DLL nicht mehr. Teste mal damit:

Option Explicit
Private Declare PtrSafe Function SystemParametersInfoA Lib "user32.dll" ( _
ByVal uAction As Long, _
ByVal uParam As Long, _
ByRef lpvParam As Any, _
ByVal fuWinIni As Long) As Long
Private Declare PtrSafe Function OleCreatePictureIndirect Lib "oleaut32.dll" ( _
ByRef PicDesc As PICT_DESC, _
ByRef RefIID As GUID, _
ByVal fPictureOwnsHandle As LongPtr, _
ByRef IPic As IPicture) As LongPtr
Private Declare PtrSafe Function CopyImage Lib "user32.dll" ( _
ByVal handle As LongPtr, _
ByVal un1 As Long, _
ByVal n1 As Long, _
ByVal n2 As Long, _
ByVal un2 As Long) As LongPtr
Private Declare PtrSafe Function IsClipboardFormatAvailable Lib "user32.dll" ( _
ByVal wFormat As Long) As Long
Private Declare PtrSafe Function OpenClipboard Lib "user32.dll" ( _
ByVal hwnd As LongPtr) As Long
Private Declare PtrSafe Function GetClipboardData Lib "user32.dll" ( _
ByVal wFormat As Long) As LongPtr
Private Declare PtrSafe Function DeleteObject Lib "gdi32.dll" ( _
ByVal hObject As LongPtr) As Long
Private Declare PtrSafe Function CLSIDFromString Lib "ole32.dll" ( _
ByVal lpsz As Any, _
ByRef pCLSID As GUID) As Long
Private Declare PtrSafe Function EmptyClipboard Lib "user32.dll" () As Long
Private Declare PtrSafe Function CloseClipboard Lib "user32.dll" () As Long
Private Type GUID
Data1 As Long
Data2 As Integer
Data3 As Integer
Data4(0 To 7) As Byte
End Type
Private Type PICT_DESC
Size As Long
Type As Long
hPic As LongPtr
hPal As LongPtr
End Type
Private Const PICTYPE_BITMAP As Long = 1
Private Const CF_BITMAP As Long = 2
Private Const IMAGE_BITMAP As Long = 0
Private Const LR_COPYRETURNORG  As Long = &H4
Private Const GUID_IPICTUREDISP As String = "{7BF80981-BF32-101A-8BBB-00AA00300CAB}"
Private Const SPI_SETDESKWALLPAPER As Long = 20
Private Const SPIF_SENDWININICHANGE As Long = &H2
Private llngptrCopy As LongPtr
Private Function Paste_Picture() As IPictureDisp
Dim lngReturn As Long, lngptrPointer As LongPtr
If CBool(IsClipboardFormatAvailable(CF_BITMAP)) Then
lngReturn = OpenClipboard(CLngPtr(Application.hwnd))
If lngReturn > 0 Then
lngptrPointer = GetClipboardData(CF_BITMAP)
llngptrCopy = CopyImage(lngptrPointer, _
IMAGE_BITMAP, 0, 0, LR_COPYRETURNORG)
Call CloseClipboard
If lngptrPointer  0 Then Set Paste_Picture = _
Create_Picture(llngptrCopy, 0&)
End If
End If
End Function
Private Function Create_Picture( _
ByVal lngptrhPic As LongPtr, _
ByVal lngptrhPal As LongPtr) As IPictureDisp
Dim udtPicInfo As PICT_DESC, udtID_IDispatch As GUID
Dim objPicture As IPictureDisp
Call CLSIDFromString(StrPtr( _
GUID_IPICTUREDISP), udtID_IDispatch)
With udtPicInfo
.Size = Len(udtPicInfo)
.Type = PICTYPE_BITMAP
.hPic = lngptrhPic
.hPal = lngptrhPal
End With
Call OleCreatePictureIndirect(udtPicInfo, _
udtID_IDispatch, 0, objPicture)
Set Create_Picture = objPicture
Set objPicture = Nothing
End Function
Private Sub CreateDesktopPicture(ByVal pvstrFileName As String, _
ByRef probjRange As Range, ByVal pvblnShowOnDesktop As Boolean)
Dim strFirstFileName As String, strSecondFileName As String
Dim objPicture As IPictureDisp
Dim objImageFile As Object
Dim objImageProcess As Object
Call OpenClipboard(Application.hwnd)
Call EmptyClipboard
Call CloseClipboard
On Error Resume Next
Do
DoEvents
Call probjRange.CopyPicture(Appearance:=xlScreen, Format:=xlBitmap)
If Err.Number = 0 Then Exit Do
Call Err.Clear
Loop
On Error GoTo 0
Set objPicture = Paste_Picture()
If Not objPicture Is Nothing Then
strFirstFileName = Environ$("TMP") & "\TMP.bmp"
Call SavePicture(Picture:=objPicture, Filename:=strFirstFileName)
strSecondFileName = "Beispiel-URL" & "\" & pvstrFileName & ".bmp"
If Dir$(PathName:=strSecondFileName)  vbNullString Then _
Call Kill(PathName:=strSecondFileName)
Set objImageFile = CreateObject(Class:="WIA.ImageFile")
Set objImageProcess = CreateObject(Class:="WIA.ImageProcess")
Call objImageFile.LoadFile(Filename:=strFirstFileName)
Call objImageProcess.Filters.Add(FilterID:=objImageProcess.FilterInfos("Crop").FilterID)
With objImageProcess.Filters(1)
.Properties("Top") = 1
.Properties("Bottom") = 0
.Properties("Left") = 1
.Properties("Right") = 0
End With
Set objImageFile = objImageProcess.Apply(Source:=objImageFile)
Call objImageFile.SaveFile(Filename:=strSecondFileName)
Set objImageFile = Nothing
Set objImageProcess = Nothing
If pvblnShowOnDesktop Then Call SystemParametersInfoA(SPI_SETDESKWALLPAPER, _
0&, strSecondFileName, SPIF_SENDWININICHANGE)
Call Kill(PathName:=strFirstFileName)
Else
MsgBox "Error - table can't show on desktop", vbCritical, "Error"
End If
Call DeleteObject(llngptrCopy)
End Sub
Gruß
Nepumuk
Anzeige
Funktioniert perfekt, vielen lieben Dank
21.10.2021 09:37:11
Dome

48 Forumthreads zu ähnlichen Themen

Anzeige
Anzeige
Anzeige

Beliebteste Forumthreads (12 Monate)

Anzeige

Beliebteste Forumthreads (12 Monate)

Anzeige
Anzeige
Anzeige