Text an notepad senden und unter bestehendem Text einfügen ?

Für allgemeine Fragen zur Programmierung mit PureBasic.
TWELVE
Beiträge: 72
Registriert: 01.04.2007 18:33

Text an notepad senden und unter bestehendem Text einfügen ?

Beitrag von TWELVE »

Ich möchte einen selektierten Text, den ich mit:

Code: Alles auswählen

Procedure.s GetSelectedEditorText(iEdId.i)
;-----------------------------------------
Protected sSelected.s, Range.CHARRANGE, iSize.i 

               SendMessage_(GadgetID(iEdId), #EM_EXGETSEL, 0, Range)

                      iSize = (Range\cpMax - Range\cpMin)
                  sSelected = Space((iSize * 2) + 1)
          
               SendMessage_(GadgetID(iEdId),#EM_GETSELTEXT, 0, sSelected)

               ProcedureReturn(sSelected)
EndProcedure 
aus einem EditorGadget hole, an ein neues oder bestehendes Notepad senden, und zwar so,
das der neue Text unter dem bestehenden eingefügt wird.

Die notepad.exe öffne ich über RunProgram() und halte es dann geöffnet, so dass ich
alle folgenden Textstücke dahin senden kann, bis entweder der User das Notepad schließt
( dann wird einfach ein neues geöffnet) oder die Applikation beendet wird.Das funktioniert.

Bisher habe ich dazu nur die folgenden zwei Methoden gefunden:

Code: Alles auswählen

1. SendMessage_(FindWindowEx_(FindWindow_("notepad",0),0,"Edit",0),#WM_SETTEXT,0,"Hallo Welt"+#CRLF$)  

2. SendMessage_(FindWindowEx_(FindWindow_("notepad",0),0,"Edit",0),#WM_PASTE,0,0) 
Beides funktioniert soweit, aber es ist noch nicht ganz das, was ich will.

1. setzt den kompletten Text im notepad, um den alten Text nicht zu überschreiben, müßte ich diesen vorher
aus dem Notepad auslesen, mit dem neuen Text kombinieren und dann wieder ins Notepad zurückschreiben.

2. der Umweg übers Clipboard funktioniert, aber ich möchte es vermeiden, Text ohne eindeutige User-Aktion ins
Clipboard zu kopieren, da es sonst beim Paste erfahrungsgemäß Überraschungen gibt.Außerdem müßte ich
irgendwie noch einen Linefeed in das Clipboard reinmogeln, damit der neue Textblock unter dem
bestehenden eingefügt wird.Den selektierten Text ins Clipboard zu befördern, biete ich per Rechtsklick
trotzdem an ( aber dann macht der User das auch selber aktiv).Evtl. könnte man das Clipboard
zwischenspeichern und dann wiederherstellen, aber ist irgendwie auch Gemurkse ;-)

Beides sind für mich nur Notlösungen, daher suche ich nach einer sauberen Lösung dafür.

Im Endeffekt soll das Notepad Textschnipsel sammeln, die der User im EditorGadget selektiert hat.
Sinn ist natürlich, manuelle Useraktionen zu verringern ( also copy to clipboard, Notepad vorholen,
Linefeed, Paste Text).
Benutzeravatar
bobobo
jaAdmin
Beiträge: 3857
Registriert: 13.09.2004 17:48
Kontaktdaten:

Re: Text an notepad senden und unter bestehendem Text einfüg

Beitrag von bobobo »

Fleisch wäre es brauchbar den Output gleich in eine Text-Datei zu schreiben
bzw. an eine vorhandene dranzuhängen.

NotePad ist doch nur zum Anzeigen der Datei da, wenn ich das richtig verstanden habe.

Das kannst Du recht flott mit einem PB-Programm und dem Editorgadget nachcoden.
Du müsstest dann nur den Textfile bei Bedarf dort neu einlesen.

Das spart dann auch gleich das API-Gekrampfe mit sendmessage und dem
Clipboard-gefrickel, das ja durchaus auchmal gerne schief gehen kann.
‮pb aktuell5.7 - windoof aktuell und sowas von 10
Ich hab Tinnitus im Auge. Ich seh nur Pfeifen.
TWELVE
Beiträge: 72
Registriert: 01.04.2007 18:33

Re: Text an notepad senden und unter bestehendem Text einfüg

Beitrag von TWELVE »

Die Idee ist vielleicht gar nicht mal so schlecht...das Notepad dient allerdings nur als "Scratchpad", sprich zum Sammeln von Text, welchen man dann
aus dem Notepad kopiert, um ihn woanders einzufügen ( eine Web Anwendung).Ein Abspeichern in eine Textdatei findet normalerweise nicht statt.
Man könnte sicher den selektierten Text in eine Textdatei senden, aber das wäre dann unsichtbar für den User.Ein offenes Notepad,
indem der Text erscheint, bietet da eine andere Rückmeldung für den User.

Ich habe auch schon überlegt, ein weiteres EditorGadget einzubauen, um damit die Funktion des Notepads zu übernehmen.
Ich habe nur leider eigentlich den Platz dafür nicht und möchte ungerne GUI Elemente zusammenquetschen, nur damit sie
auf den Bildschirm passen.Mit ein paar Tricks könnte man das sicher lösen ( z.B. Gadgets bei Bedarf halbieren etc.), aber
ich möchte eben im Moment nicht soviel Aufwand in eine relativ einfache Funktion stecken, die quasi nebenbei abfällt.

Weitere Lösungsansätze oder Lösungen ?
Benutzeravatar
Sicro
Beiträge: 955
Registriert: 11.08.2005 19:08
Kontaktdaten:

Re: Text an notepad senden und unter bestehendem Text einfüg

Beitrag von Sicro »

TWELVE hat geschrieben:Ich habe auch schon überlegt, ein weiteres EditorGadget einzubauen, um damit die Funktion des Notepads zu übernehmen.
Ich habe nur leider eigentlich den Platz dafür nicht und möchte ungerne GUI Elemente zusammenquetschen,
Neues Fenster mit EditorGadget? Wenn du Notepad offen hast, ist es ja auch nicht anders.
Bild
Warum OpenSource eine Lizenz haben sollte :: PB-CodeArchiv-Rebirth :: Pleasant-Dark (Syntax-Farbschema) :: RegEx-Engine (kompiliert RegExes zu NFA/DFA)
Manjaro Xfce x64 (Hauptsystem) :: Windows 10 Home (VirtualBox) :: Neueste PureBasic-Version
TWELVE
Beiträge: 72
Registriert: 01.04.2007 18:33

Re: Text an notepad senden und unter bestehendem Text einfüg

Beitrag von TWELVE »

Also das Theater mit einem Extra Editor Gadget habe ich jetzt erstmal vermieden...zuviel Code für eine simple Funktion !

Aktuell mache ich es jetzt so:

Aktuelles Clipboard abspeichern:

Code: Alles auswählen

Global ClipBoardSave.s
...
ClipBoardSave.s = GetClipboardText()
Selektierten Text ins Clipboard befördern:

Code: Alles auswählen

SendMessage_(GadgetID(Editor_1), #WM_COPY,0,0)
Text ins notepad einfügen per Paste:

Code: Alles auswählen

SendMessage_(FindWindowEx_(FindWindow_("notepad",0),0,"Edit",0),#WM_PASTE,0,0)
Linefeed an Editor hinterhersenden:

Code: Alles auswählen

w$="Unbenannt - Editor" ; Specifies target window name. 
Delay(1000) : SendKeys(0,w$,#CRLF$) ; text to send 
SendKeys ist in einem externen Include File mit folgendem Code:

Code: Alles auswählen

; German forum:
; Author: Danilo
; Date: 07. April 2003
; OS: Windows
; Demo: No


; Posted 07 April 2003 by Danilo on german forum

;SendKeys(handel,Window$,Keys$) 

;Handel ......... ist ein Handel zu einen Fenster bekommst du wenn du das Fenster erzeugst. 
;Window$ ........ Ist der Name des Fesnters, wenn du den Handel nicht kennst. In dem Fall gibt man dan Handel = 0 an. 
;Keys$ .......... Sind die Tasten die du schicken möchtest, wobei du Sondertasten in {} Einschliest (zb. {CONTROLDOWN}) 

; SendKeys procedure by PB -- do whatever you want with it. :) 
; Syntax: r=SendKeys(handle,window$,keys$) ; r = 0 for failure. 
; Specify either a handle or window$ title to type to, but not both! 
; You cannot type curly braces { } as part of the keystrokes, sorry! 
; 
Procedure SendKeys(handle,window$,keys$) 
If window$<>"" : handle=FindWindow_(0,window$) : EndIf ; Use window$ instead of handle. 
   If IsWindow_(handle)=0 ; Does the target window actually exist? 
      ProcedureReturn 0 ; Nope, so report 0 for failure to type. 
   Else 
   ; This block gives the target window the focus before typing. 
   thread1=GetWindowThreadProcessId_(GetForegroundWindow_(),0) 
   thread2=GetWindowThreadProcessId_(handle,0) 
   If thread1<>thread2 : AttachThreadInput_(thread1,thread2,#True) : EndIf 
      SetForegroundWindow_(handle) ; Target window now has the focus for typing. 
      Delay(125) ; 1/8 second pause before typing, to prevent fast CPU problems. 
      ; Now the actual typing starts. 
      For r=1 To Len(keys$) 
          vk$=Mid(keys$,r,1) 
          If vk$="{" ; Special key found. 
             s=FindString(keys$,"}",r+1)-(r+1) ; Get length of special key. 
             s$=Mid(keys$,r+1,s) ; Get special key name. 
             Select s$ ; Get virtual key code of special key. 
                Case "ALTDOWN" : keybd_event_(#VK_MENU,0,0,0) ; Hold ALT down. 
                Case "ALTUP" : keybd_event_(#VK_MENU,0,#KEYEVENTF_KEYUP,0) ; Release ALT. 
                Case "BACKSPACE" : vk=#VK_BACK 
                Case "CONTROLDOWN" : keybd_event_(#VK_CONTROL,0,0,0) ; Hold CONTROL down. 
                Case "CONTROLUP" : keybd_event_(#VK_CONTROL,0,#KEYEVENTF_KEYUP,0) ; Release CONTROL. 
                Case "DELETE" : vk=#VK_DELETE 
                Case "DOWN" : vk=#VK_DOWN 
                Case "END" : vk=#VK_END 
                Case "ENTER" : vk=#VK_RETURN 
                Case "F1" : vk=#VK_F1 
                Case "F2" : vk=#VK_F2 
                Case "F3" : vk=#VK_F3 
                Case "F4" : vk=#VK_F4 
                Case "F5" : vk=#VK_F5 
                Case "F6" : vk=#VK_F6 
                Case "F7" : vk=#VK_F7 
                Case "F8" : vk=#VK_F8 
                Case "F9" : vk=#VK_F9 
                Case "F10" : vk=#VK_F10 
                Case "F11" : vk=#VK_F11 
                Case "F12" : vk=#VK_F12 
                Case "ESCAPE" : vk=#VK_ESCAPE 
                Case "HOME" : vk=#VK_HOME 
                Case "INSERT" : vk=#VK_INSERT 
                Case "LEFT" : vk=#VK_LEFT 
                Case "PAGEDOWN" : vk=#VK_NEXT 
                Case "PAGEUP" : vk=#VK_PRIOR 
                Case "PRINTSCREEN" : vk=#VK_SNAPSHOT 
                Case "RETURN" : vk=#VK_RETURN 
                Case "RIGHT" : vk=#VK_RIGHT 
                Case "SHIFTDOWN" : shifted=1 : keybd_event_(#VK_SHIFT,0,0,0) ; Hold SHIFT down. 
                Case "SHIFTUP" : shifted=0 : keybd_event_(#VK_SHIFT,0,#KEYEVENTF_KEYUP,0) ; Release SHIFT. 
                Case "TAB" : vk=#VK_TAB 
                Case "UP" : vk=#VK_UP 
             EndSelect 
             If Left(s$,3)<>"ALT" And Left(s$,7)<>"CONTROL" And Left(s$,5)<>"SHIFT" 
                keybd_event_(vk,0,0,0) : keybd_event_(vk,0,#KEYEVENTF_KEYUP,0) ; Press the special key. 
             EndIf 
             r=r+s+1 ; Continue getting the keystrokes that follow the special key. 
          Else 
             vk=VkKeyScanEx_(Asc(vk$),GetKeyboardLayout_(0)) ; Normal key found. 
             If vk>304 And shifted=0 : keybd_event_(#VK_SHIFT,0,0,0) : EndIf ; Due to shifted character. 
             keybd_event_(vk,0,0,0) : keybd_event_(vk,0,#KEYEVENTF_KEYUP,0) ; Press the normal key. 
             If vk>304 And shifted=0 : keybd_event_(#VK_SHIFT,0,#KEYEVENTF_KEYUP,0) : EndIf ; Due to shifted character. 
          EndIf 
      Next 
      If thread1<>thread2 : AttachThreadInput_(thread1,thread2,#False) : EndIf ; Finished typing to target window! 
      keybd_event_(#VK_MENU,0,#KEYEVENTF_KEYUP,0) ; Release ALT key if user forgot. 
      keybd_event_(#VK_CONTROL,0,#KEYEVENTF_KEYUP,0) ; Release CONTROL key if user forgot. 
      keybd_event_(#VK_SHIFT,0,#KEYEVENTF_KEYUP,0) ; Release SHIFT key if user forgot. 
      ProcedureReturn 1 ; Report successful typing! :) 
   EndIf 
EndProcedure 
; 
m$= "This example types some text to Notepad, then clears and closes it."+Chr(13) 
m$=m$+"Open a new Notepad window, then click the OK button and watch! :)" 
MessageRequester("SendKeys example",m$,#MB_ICONINFORMATION) 
; 
RunProgram("c:\winnt\notepad.exe","","",0) 
w$="Untitled - Notepad" ; Specifies target window name. 
Delay(1000) : SendKeys(0,w$,"This is a test!") ; Type some dummy text. 
Delay(1000) : SendKeys(0,w$,"{CONTROLDOWN}a{CONTROLUP}") ; Select it all. 
Delay(1000) : SendKeys(0,w$,"{DELETE}")      ; Delete it. 

Delay(1000) : SendKeys(0,w$,"{CONTROLDOWN}p{CONTROLUP}") 

;Delay(1000) : SendKeys(0,w$,"{ALTDOWN}{F4}") ; Close the Notepad Window
; IDE Options = PureBasic v4.00 (Windows - x86)
; Folding = -
Clipboard wieder herstellen:

Code: Alles auswählen

SetClipboardText(ClipBoardSave.s)

Ein Haufen Aufwand und Code für ein bißchen Funktionalität....

1. Es funktioniert...aber es ist nicht cool.100 Zeilen Source einkompilieren, um ein LF an ein notepad zu senden ?
Außerdem das ganze Gefummel mit dem Clipboard...

2. mich stört auch, dass ich das notepad ausschließlich über seinen Namen oder Fenstertitel identifizieren kann.
Ich habe eine Prozess ID meines Notepads...aber wie kann ich die hier verwenden ?

Sobald ein zweites Notepad offen ist ( und ich kann das nicht kontrollieren), geht es schief, weil ich das Notepad weder
über den Titel noch über den Programmnamen eindeutig identifizieren kann, meine o.g. WinAPI Befehle aber eben damit arbeiten.
Benutzeravatar
ts-soft
Beiträge: 22292
Registriert: 08.09.2004 00:57
Computerausstattung: Mainboard: MSI 970A-G43
CPU: AMD FX-6300 Six-Core Processor
GraKa: GeForce GTX 750 Ti, 2 GB
Memory: 16 GB DDR3-1600 - Dual Channel
Wohnort: Berlin

Re: Text an notepad senden und unter bestehendem Text einfüg

Beitrag von ts-soft »

TWELVE hat geschrieben: Sobald ein zweites Notepad offen ist ( und ich kann das nicht kontrollieren), geht es schief, weil ich das Notepad weder
über den Titel noch über den Programmnamen eindeutig identifizieren kann, meine o.g. WinAPI Befehle aber eben damit arbeiten.
Du hast doch ein Handle, das kann in der Procedure von Danilo auch übergeben werden, als erster Parameter. Das ist Eindeutig und da kann es keine Verwechslungen geben.

Code: Alles auswählen

SendMessage_(FindWindowEx_(FindWindow_("notepad",0), ...
Und FindWindowEx_(FindWindow_(..., das gibt auch ein Handle zurück.

Gruß
Thomas
PureBasic 5.73 LTS | SpiderBasic 2.30 | Windows 10 Pro (x64) | Linux Mint 20.1 (x64)
Nutella hat nur sehr wenig Vitamine. Deswegen muss man davon relativ viel essen.
Bild
TWELVE
Beiträge: 72
Registriert: 01.04.2007 18:33

Re: Text an notepad senden und unter bestehendem Text einfüg

Beitrag von TWELVE »

ts-soft hat geschrieben:
TWELVE hat geschrieben: Sobald ein zweites Notepad offen ist ( und ich kann das nicht kontrollieren), geht es schief, weil ich das Notepad weder
über den Titel noch über den Programmnamen eindeutig identifizieren kann, meine o.g. WinAPI Befehle aber eben damit arbeiten.
Du hast doch ein Handle, das kann in der Procedure von Danilo auch übergeben werden, als erster Parameter. Das ist Eindeutig und da kann es keine Verwechslungen geben.

Code: Alles auswählen

SendMessage_(FindWindowEx_(FindWindow_("notepad",0), ...
Und FindWindowEx_(FindWindow_(..., das gibt auch ein Handle zurück.

Gruß
Thomas
FindWindow...sucht nach einem Fenster namens "notepad", davon können aber mehrere offen sein.Das ist nicht eindeutig.
Und selbst wenn ich einen Window Handle kennen würde, dann könnte ich den Danilos Procedure übergeben, aber der
Text selber ( Clipboard WM_PASTE) wird nach wie vor in ein notepad kopiert, welches ich lediglich über einen Window Title
identifiziere.

Ich habe aber auch kein Handle, ich öffne notepad mit RunProgram() und bekomme den Handle des Prozesses zurück.Den Handle des notepad
Windows kenne ich nicht, woher auch.Kenne ich den Window Handle nicht, kann ich nur einen Window Title angeben.
Der Titel eines Notepads ist je nach Windows Version und Sprache verschieden ( auf deutschen W7 Systemen z.B. heißt
es "Unbenannt - Editor") und alle nicht abgespeicherten Notepads heißen so.

Ich muß sicherstellen, dass der Text nur in "mein" Notepad kopiert wird und andere Notepads unangetastet bleiben.

Wie kann ich nun den Text an ein eindeutiges Notepad senden ? Entscheidend ist der RunProgramm Handle oder auch
gerne die PID.
TWELVE
Beiträge: 72
Registriert: 01.04.2007 18:33

Re: Text an notepad senden und unter bestehendem Text einfüg

Beitrag von TWELVE »

Ich habe eine Lösung gefunden.

Ich mache es jetzt so:

Window Handle meines notepads herausfinden:

Code: Alles auswählen

EnableExplicit

Define Prog_ID.l
Define Prog_PID.l
Define Prog_hWnd.l

Procedure.l ProcID2hWnd(ProcID.l)
  
  Protected hwnd.l
  Protected ProcTaskID.l
  
  hwnd = FindWindow_(#Null, #Null)
  
  While hwnd <> 0
    
    GetWindowThreadProcessId_(hwnd, @ProcTaskID)
    
    If ProcTaskID = ProcID
      ProcedureReturn hwnd
    EndIf
    
    hwnd = GetWindow_(hwnd, #GW_HWNDNEXT)
    
  Wend
  
EndProcedure

Prog_ID = RunProgram("notepad.exe", "", "", #PB_Program_Open)

If Prog_ID 
  
  Prog_PID = ProgramID(Prog_ID)
  
  Debug "Prog_ID: "  + Str(Prog_ID)
  Debug "Prog_PID: " + Str(Prog_PID)
  
  Repeat
    Prog_hWnd = ProcID2hWnd(Prog_PID)
    If Prog_hWnd : Break : EndIf
  ForEver
  
  Debug "Prog_hWnd: " + Str(Prog_hWnd)

EndIf
Quelle:

http://www.purebasic.fr/german/viewtopi ... &hilit=PID

Den bisher benutzten Clipboard Paste ins Notepad basierend auf dem Window Namen:

Code: Alles auswählen

SendMessage_(FindWindowEx_(FindWindow_("notepad",0),0,"Edit",0),#WM_PASTE,0,0)

ersetze ich durch:

Code: Alles auswählen

hWndEdit = FindWindowEx_(Prog_hWnd, 0, "Edit", 0)
SendMessage_(hWndEdit,#WM_PASTE,0,0)

bzw. kürzere Form:

SendMessage_(FindWindowEx_(Prog_hWnd, 0, "Edit", 0),#WM_PASTE,0,0)
Der SendKeys Procedure ( siehe oben ) übergebe ich nun statt dem Window Namen den Window Handle ( hwnd)


Alt:

w$="Unbenannt - Editor" ; Specifies target window name
Delay(1000) : SendKeys(0,w$,#CRLF$) ; text to send

Neu:

Delay(1000) : SendKeys(Prog_hWnd,"",#CRLF$) ; text to send
Der Name des Windows ist wie gesagt problematisch bei mehreren notepads und außerdem ist der Name je nach Windows Version
und Sprache auch noch verschieden.

Das funktioniert einwandfrei !

Mit dem kleinem Umweg über das Clipboard ( siehe oben) kann ich insofern leben, dass ich das Clipboard nach der Aktion wiederherstelle
und so der User keine bösen Überraschungen beim Paste erlebt.

Mit dem obigen Code zur Ermittlung des Window Handles aus der PID hatte ich ein merkwürdiges Verhalten.Ich prüfe erst, ob mein Notepad
schon geöffnet ist und wenn das nicht der Fall ist, öffne ich eins und frage die hwnd ab.Wenn es schon offen ist, frage ich wieder die
hwnd ab und das hat nicht funktioniert.Die hwnd war dann nicht die von meinem notepad.Ich habe das jetzt so gelöst, dass ich die
hwnd abspeichere, sobald ich sie nach dem Öffnen des Notepads ermittelt habe.Das ist eh cleverer, weil es Code und Zeit spart,
aber mich würde trotzdem interessieren, warum das o.g. ProcID2hWnd(ProcID.l) beim weiteren Aufrufen die hwnd nicht zuverlässig ermittelt.


Hat jemand vielleicht eine bessere Methode wie das ProcID2hWnd(ProcID.l) hier, um aus einer PID den Window Handle zu ermitteln ?
Benutzeravatar
NicTheQuick
Ein Admin
Beiträge: 8675
Registriert: 29.08.2004 20:20
Computerausstattung: Ryzen 7 5800X, 32 GB DDR4-3200
Ubuntu 22.04.3 LTS
GeForce RTX 3080 Ti
Wohnort: Saarbrücken
Kontaktdaten:

Re: Text an notepad senden und unter bestehendem Text einfüg

Beitrag von NicTheQuick »

Die Wiederherstellung des Clipboards funktioniert aber nur für einfache Strings. Im Clipboard können ja auch Bilder oder Richtext-formatierte Strings und sonstiger Kram sein. Ich weiß nicht genau, was noch alles möglich ist. Mit Purebasic kriegt man jedenfalls nur den Reintext.
Bild
auser
Beiträge: 58
Registriert: 17.05.2011 10:56

Re: Text an notepad senden und unter bestehendem Text einfüg

Beitrag von auser »

TWELVE hat geschrieben:eine bessere Methode wie das ProcID2hWnd(ProcID.l) hier, um aus einer PID den Window Handle zu ermitteln ?
Stand/stehe vor einem ähnlichen Problem und hab keine schöne Lösung, dafür aber noch weitere Probleme im Angebot /:-> :mrgreen:


Mein Stand bisher:

Handle über PID rauszufinden kann sich als unmöglich erweisen weil viele Programme Instanzen verwenden und es hierfür keinen Windows-Standard gibt. Beispiel: Firefox macht ein weiteres Tab auf, Word ein neues Dokument usw. Unter'm Strich erweist sich da auch ShellExecuteEx_() mit der Mask SEE_MASK_NOCLOSEPROCESS als nutzlos. Das ist vermtulich auch der Grund warum PBs RunProgram() gern mal -1 zurück gibt wenn man ein Program nicht über die EXE sondern (erfolgreich) über einen URL-Aufruf ausführt (z.B. http://). Man würde sich diese Funktion zwar manchmal wünschen z.B. um zu sehen ob das Program noch läuft das man dem User da aufgemacht hat oder eben um sicher zu gehen daß man seinen Mist nicht automatisiert wild in das falsche Fenster reintextet und eine Katastrophe anrichtet, kann aber mangels Standard nicht funktionieren (nur für den Fall daß man auf die Idee kommen würde hier ein paar Tage in der WinAPI eine Lösung zu suchen) - oder eben nur dann wenn es sicher nur eine Instanz gibt die da läuft.

Dann kommt aber schon das nächste Problem:

SendMessage_() ist in vielen Belangen unzureichend oder bringt andere Probleme mit sich. BlockInput_() wiederum ...das sowohl für SendInput_() als auch für keybd_event_() nett gewesen wäre funktioniert in neueren Windows-Versionen nur noch mit Adminrechten. Was sich MS dabei gedacht hat ist mir ehrlich gesagt schleierhaft, weil es ja letztlich dazu führt daß ich als Admin weniger Rechte habe. Ok ich hab das Recht mich erfolgreich mit Adminrechten am Input blocken zu lassen. Ein User hat dieses Recht nicht und behält somit das (eigentlich stärkere) Recht weiterhin ins Input reinzufummeln. Auch AttachThreadInput hat sich hier als ziemlich nutzlos erwiesen (und / oder löst natürlich immer noch nicht das Problem daß man erst mal das Fenster erraten muss).


So oder so ... zumindest Notepad konnte ich damit mit halbwegs "hoher Trefferquote" (und es ist ein Graus das überhaupt so schreiben zu müssen weil der User immer noch reinfunken kann) über SendInput bespaßen:

Code: Alles auswählen

Structure cb_inout
  pid.q
  handle.l
EndStructure 
Procedure EnumWindowsCallback(handle.l, *h.cb_inout)
    Protected pid.q = 0
    GetWindowThreadProcessId_(handle, @pid)
    If *h\pid = pid And IsWindowVisible_(handle)
      *h\handle = handle
      ProcedureReturn(0)  
    Else
      ProcedureReturn(1)
    EndIf 
EndProcedure 
Procedure FindWindowHopefully(pid.q)
  Protected h.cb_inout 
  h\pid = pid
  
  EnumWindows_(@EnumWindowsCallback(), @h)
  ProcedureReturn(h\handle)
EndProcedure 
Antworten