 |
Das deutsche QBasic- und FreeBASIC-Forum Für euch erreichbar unter qb-forum.de, fb-forum.de und freebasic-forum.de!
|
Vorheriges Thema anzeigen :: Nächstes Thema anzeigen |
Autor |
Nachricht |
TimesChange
Anmeldungsdatum: 20.11.2013 Beiträge: 85
|
Verfasst am: 06.02.2014, 17:12 Titel: Screenshot speichern und als Desktop-Hintergrund setzen? |
|
|
Wie kann ich es schaffen, dass ein Programm von seinem eigenen Fenster einen Screenshot macht, speichert, und dieses sodann als Desktophintergrund (Win XP / 7 / 8) verwendet wird?
Zum Thema Screenshot habe ich ein Beispiel hier http://forum.qbasic.at/viewtopic.php?t=8206 und hier http://www.freebasic-portal.de/code-beispiele/grafik-und-fonts/screenshot-erstellen-grafikimage-139.html gefunden.
Noch nicht klar ist mir wie ich hier das "eigene" Fenster auswähle.
Und zuvor die Frage, ob ich aus einem Programm heraus überhaupt so einfach den Desktop-Hintergrund verändern kann.
Für die, die's interessiert, was ich damit will:
Ich habe mir ein kleines Programm geschrieben, dass mir einen Kalender in 3-Monats-Übersicht anzeigt. In der Mitte der aktuelle Monat, links Vormonat,...
So in der Art eines kleinen Tischkalenders, damit ich auf die Schnelle z.B. während eines Telefonats sehen, welcher Wochentag denn der z.B. 27.02 ist. Im Programm kann man natürlich auch vor- und zurückblättern, aber meist reicht mir das aktuelle "Kalenderblatt".
Dazu müsste das Programm nicht ständig laufen (und mir einen "wertvollen" Platz in der Task-Leiste belegen). Daher der Gedanke, dass das Programm beim Aufruf ein Abbild auf das Desktop legt. Das habe ich mit einem Klick immer im Blick.
Grüße
Rainer |
|
Nach oben |
|
 |
MOD Fleißiger Referenzredakteur

Anmeldungsdatum: 10.09.2007 Beiträge: 1003
|
Verfasst am: 06.02.2014, 19:30 Titel: |
|
|
Du musst den Handle deines Fensters übergeben und den bekommst du mit ScreenControl in etwa so:
Code: | ScreenControl FB.GET_WINDOW_HANDLE, handle |
Den kannst du dann mit GetWindowRect nutzen. Oder aber du gibst ihm einfach 0 als Handle, dann nimmt er das aktuelle Fenster.
Das Bild wirst du dann mit Hilfe der WinAPI auch sicher irgendwie als Hintergrund setzen können. Googlen sollte helfen, oder einer der WinAPI-Profis hier. |
|
Nach oben |
|
 |
grindstone
Anmeldungsdatum: 03.10.2010 Beiträge: 1278 Wohnort: Ruhrpott
|
Verfasst am: 06.02.2014, 19:58 Titel: |
|
|
Das ist - zumindest bei XP - ganz einfach:
Um an das Fensterhandle zu kommen, das du an CaptureWindow(... übergeben musst, fügst du in dein Programm möglichst weit vorne die Zeilen Code: | #Include Once "windows.bi"
Dim As HANDLE hWndDiesesFenster
hWndDiesesFenster = GetForegroundWindow() | ein.
Nachdem du deinen ersten Screenshot erstellt und abgespeichert hast, rufst du die Eigenschaften von Anzeige auf (Rechtsklick auf den Desktp) und setzt dann über Eigenschaften > Desktop > Durchsuchen den Screenshot als neues Hitergrundbild.
Wenn du dann noch eine Verknüpfung zu deinem Kalenderprogramm in den Autostartordner legst, hast du bei jedem Start einen "frischen" Kalender.
Gruß
grindstone _________________ For ein halbes Jahr wuste ich nich mahl wie man Proggramira schreibt. Jetzt bin ich einen! |
|
Nach oben |
|
 |
TimesChange
Anmeldungsdatum: 20.11.2013 Beiträge: 85
|
Verfasst am: 06.02.2014, 21:09 Titel: |
|
|
Ok, der Screenshot des Fensters sollte prinzipiell hinzubekommen sein.
grindstone hat Folgendes geschrieben: | ...
Wenn du dann noch eine Verknüpfung zu deinem Kalenderprogramm in den Autostartordner legst, hast du bei jedem Start einen "frischen" Kalender.
|
Ah ja, Windows lädt die Datei also bei jedem Start neu?
Lieber wär's mir aber, wenn ich das Setzen des Hintergrund aktiv über das Programm steuern könnte, da ich nicht täglich neu starte.
Wenn jemand weiß, wie das in FB möglich ist, wäre das super.
Ich habe z.B. hier http://msdn.microsoft.com/en-us/library/windows/desktop/ms724947%28v=vs.85%29.aspx#Desktop was gefunden: SPI_SETDESKWALLPAPER
Aber die Anwendung in FB übersteigt meine Fähigkeiten...
Grüße
Rainer |
|
Nach oben |
|
 |
St_W

Anmeldungsdatum: 22.07.2007 Beiträge: 956 Wohnort: Austria
|
Verfasst am: 06.02.2014, 22:17 Titel: |
|
|
Die Anwendung dieser Funktion ist für dieses Ziel sehr einfach: Code: | #Include "windows.bi"
SystemParametersInfo(SPI_SETDESKWALLPAPER, 0, @"parseval.jpg", SPIF_UPDATEINIFILE Or SPIF_SENDWININICHANGE) |
Hinweis: Wenn du den String nicht statisch angibst, musst du StrPtr anstatt @ verwenden.
Weitere Infos zum setzen des Bildschirmhintergrunds findest du z.B. hier:
http://code.msdn.microsoft.com/windowsdesktop/CSSetDesktopWallpaper-2107409c (die essentiellen Teile dieses C# Code kann relativ einfach auf FB übertragen werden) _________________ Aktuelle FreeBasic Builds, Projekte, Code-Snippets unter http://users.freebasic-portal.de/stw/
http://www.mv-lacken.at Musikverein Lacken (MV Lacken) |
|
Nach oben |
|
 |
TimesChange
Anmeldungsdatum: 20.11.2013 Beiträge: 85
|
Verfasst am: 06.02.2014, 22:50 Titel: |
|
|
Danke für den Hinweis - sehe ich mir genau an wenn ich soweit bin
Aber ich komme schon vorher nicht weiter...
Ich habe die im Forum gefundenen Funktionen in ein Miniprogramm eingebaut:
Code: | #include once "windows.bi"
#include once "file.bi"
Declare Function CaptureWindow( ByVal hwndSrc As HWND) As Any Ptr
Declare function screenshot (byval file as string="", byref im as any ptr) as integer
Dim As HANDLE hWndDiesesFenster
Dim as Integer E
screenres 97*8, 10 *16
width 97, 10
Print "Ich bin nur ein dummes Fenster und mach sonst nichts..."
hWndDiesesFenster = GetForegroundWindow()
E= screenshot ("screen", hWndDiesesFenster)
Print "Ergebnis: ";E
Sleep
End
'**********************************************************
Function CaptureWindow( ByVal hwndSrc As HWND) As Any Ptr
hwndSrc = GetForegroundWindow()
SetForegroundWindow(hWndSrc)
Sleep 30 'SetForegroundWindow etwas Zeit geben
Dim As RECT r
GetWindowRect(hWndSrc, @r) 'Fenstergroesse feststellen
Dim As Integer b = r.right - r.left
Dim As Integer h = r.bottom - r.top
Dim As Any Ptr img = ImageCreate(b, h)
b = (b+3) and -4 'Bildbreite glatt durch 4 teilbar
Dim As HDC hdcSrc = GetWindowDC(hWndSrc)
Dim As HDC hdcMem = CreateCompatibleDC(hdcSrc)
Dim As HBITMAP hBmp = CreateCompatibleBitmap(hdcSrc, b, h)
SelectObject(hdcMem, hBmp)
BitBlt(hdcMem, 0, 0, b, h, hdcSrc, 0, 0, SRCCOPY)
Dim As BITMAPINFO bmi
With bmi.bmiHeader
.biSize = SizeOf(BITMAPINFOHEADER)
.biWidth = b 'breite
.biHeight = -h '-hoehe (sonst Kopfstand)
.biPlanes = 1
.biCompression = BI_RGB
.biBitCount = 32
End With
If (img) Then 'Bilddaten in das Image kopieren
GetDIBits(hdcMem, hBmp, 0, h, img + 32, @bmi, DIB_RGB_COLORS)
End If
DeleteObject(hBmp)
DeleteDC(hdcMem)
ReleaseDC(hWndSrc, hdcSrc)
Return img
IMAGEDESTROY img
End Function
function screenshot (byval file as string="", byref im as any ptr) as integer
dim as HWND hw
hw=20
im=CaptureWindow(hw)
if not im=0 then
if not file="" then
bsave file,im,6400
if fileexists(file) then
return 2
else
return 0
end if
else
return 1
end if
else
return -1
end if
end function |
Immerhin stürzt das Programm nicht ab (der Compiler gibt nur eine Warnmeldung wegen der mir unverständlichen Zuweisung "hw = 20" in function screenshot).
Aber die Datei besteht im wesentlichen aus "0".
Ich gebe offen zu , dass ich wenig Ahnung habe, was ich das zusammen gestöpselt habe. Vielleicht kann mir trotzdem jemand helfen, das Programm funktionsfähig zu bekommen.
Grüße
Rainer
P.S.: Die feste Größe bei BSAVE in SCREENSHOT von 6400 kann wohl auch nicht stimmen. Aber das ist sicher nicht meine Hauptproblem.
Das verlinkte C++ Projekt habe ich mir angesehen. Aber das ist mir zu hoch... |
|
Nach oben |
|
 |
Jojo alter Rang

Anmeldungsdatum: 12.02.2005 Beiträge: 9736 Wohnort: Neben der Festplatte
|
Verfasst am: 06.02.2014, 23:44 Titel: |
|
|
Wozu die ganzen Umstände, wenn du doch eh einen FB-SCREEN verwendest? Um von dem einen "Screenshot" anzufertigen, brauchst du keine WinAPI, da reicht doch das FB-Hausmittel BSAVE völlig aus.
Aus der FB-Referenz:
Code: |
' Gesamten Bildschirm als Bitmap speichern
BSAVE "hello.bmp", 0 |
Dein Programm enthält sowieso verdächtigen Code: Code: |
Return img
IMAGEDESTROY img |
Der Code nach Return wird nie ausgeführt, es handelt sich hierbei also um ein Speicherleck, was nach kürzester Zeit jede Menge Speicher anhäuft, wenn das Programm in einer Schleife Screenshots erzeugt. Soviel zum Thema Speicherbedarf deiner Programme optimieren - erst mal vor der eigenen Haustür kehren, bevor man sich um die 1MB Sorgen macht, die FB (laut Taskmanager, sei dazu gesagt) von sich aus benötigt. _________________ » Die Mathematik wurde geschaffen, um Probleme zu lösen, die es nicht gäbe, wenn die Mathematik nicht erschaffen worden wäre.
 |
|
Nach oben |
|
 |
TimesChange
Anmeldungsdatum: 20.11.2013 Beiträge: 85
|
Verfasst am: 07.02.2014, 01:05 Titel: |
|
|
Jojo hat Folgendes geschrieben: | Wozu die ganzen Umstände... |
Ja, was soll ich dazu sagen ... schön dass es auch einfach geht
Funktioniert ja wunderbar!
Jojo hat Folgendes geschrieben: | Dein Programm enthält sowieso verdächtigen Code:
Der Code nach Return wird nie ausgeführt, es handelt sich hierbei also um ein Speicherleck... Soviel zum Thema Speicherbedarf deiner Programme optimieren - erst mal vor der eigenen Haustür kehren, bevor man sich um die 1MB Sorgen macht... |
Hey, das ist nicht meine Haustüre, die ist doch nur geklaut
Leute, Ihr seid der Hammer!
Mit diesen: Code: | Sub ScreenShot
Dim as String WallPaper
Wallpaper = ExePath() + "Kalender.bmp"
BSave (Wallpaper, 0)
SystemParametersInfo(SPI_SETDESKWALLPAPER, 0, StrPtr(Wallpaper), SPIF_UPDATEINIFILE Or SPIF_SENDWININICHANGE)
End Sub |
lächerlichen 4 Zeilen macht mein Programm ein Selbstbildnis und verewigt sich auf dem Desktop.
Wär' schön gewesen, wenn ich selber draufgekommen wäre, aber ich freue mich auch so!
Viele Grüße und Danke
Rainer |
|
Nach oben |
|
 |
TimesChange
Anmeldungsdatum: 20.11.2013 Beiträge: 85
|
Verfasst am: 07.02.2014, 01:21 Titel: |
|
|
Weil ich so happy bin, noch ein (ganz herkömmlich erstellter) Screenshot von meinem Desktop:
Ja, das sieht sicher bisschen popelig aus, die Farben (die werden nach der Umwandlung in jpg eh falsch dargestellt) sind Geschmackssache, aber es ist von der Funktion ziemlich genau das was ich wollte:
Mit einem Klick sehe ich die aktuelle Kalenderübersicht, und es läuft noch nicht einmal ein Programm dafür im Hintergrund (ganz egal ob 100 KB oder 10 MB )
Grüße
Rainer |
|
Nach oben |
|
 |
Jojo alter Rang

Anmeldungsdatum: 12.02.2005 Beiträge: 9736 Wohnort: Neben der Festplatte
|
Verfasst am: 07.02.2014, 02:50 Titel: |
|
|
TimesChange hat Folgendes geschrieben: | Hey, das ist nicht meine Haustüre, die ist doch nur geklaut |
Mag sein, aber der Kommentar musste in diesem Kontext einfach sein.  _________________ » Die Mathematik wurde geschaffen, um Probleme zu lösen, die es nicht gäbe, wenn die Mathematik nicht erschaffen worden wäre.
 |
|
Nach oben |
|
 |
TimesChange
Anmeldungsdatum: 20.11.2013 Beiträge: 85
|
Verfasst am: 10.02.2014, 01:22 Titel: |
|
|
Jaja, - ich hatte auch nichts anderes erwartet
Da ich meinen Beitrag oben nicht mehr ändern kann: Da ist noch ein kleiner Fehler drin; es fehlt der Backslash : Code: | Wallpaper = ExePath() + "\Kalender.bmp" |
Seltsamerweise wird auch mit der fehlerhaften Version das Bild auf dem Desktop angezeigt, aber so ist es sauberer...
Da mir das graue Rechteck auf meinem einfarbigem Desktop nicht so gut gefiel, habe ich noch anpassbare Farben ergänzt, sieht dann bei mir so aus:
Falls übrigens jemand Interesse haben sollte, stelle ich den Quellcode gerne zur Verfügung. Im vollen Bewusstsein, dass die "Schöpfungshöhe" im Vergleich zu dem was sonst hier gezeigt wird, sehr bescheiden ist.
Aber ihr merkt vermutlich: Ich bin selber total begeistert, weil das Programm für mich unglaublich praktisch ist
Grüße
Rainer |
|
Nach oben |
|
 |
|
|
Du kannst keine Beiträge in dieses Forum schreiben. Du kannst auf Beiträge in diesem Forum nicht antworten. Du kannst deine Beiträge in diesem Forum nicht bearbeiten. Du kannst deine Beiträge in diesem Forum nicht löschen. Du kannst an Umfragen in diesem Forum nicht mitmachen.
|
|