Walka ze schowkiem i wklejaniem z niego zawartosci

0

Czesc,
mam dziwny problem z delphi xe 5 , win7...

Chodzi o to, ze kopiuje sobie cos jakis tekst za pomocą symulacji ctrl + c

 keybd_event(VK_CONTROL, MapVirtualKey(VK_CONTROL, 0), 0, 0);
keybd_event(Ord('C'), MapVirtualKey(Ord('C'), 0), 0, 0);
keybd_event(Ord('C'), MapVirtualKey(Ord('C'), 0), KEYEVENTF_KEYUP, 0);
keybd_event(VK_CONTROL, MapVirtualKey(VK_CONTROL, 0), KEYEVENTF_KEYUP, 0)

tekst jest niby w schowku,

i teraz chcialbym owy tekst przypisac programowalnie do kontrolki Edit1.Text.
Nie potrafie tego zrobic.

Zaprzezylem do dzialania unit ClipBoard i tam probowal cos w stylu,
ClipBoard.AsText.... nie dziala.
Pokazuje ze schowek jest pusty,
tak jakby Ctrl+c kopiowalo do innego schowka.

Musze uzyc kopiowania za pomoca symulacji, jednak gdzie jest ten tekst skopiowany?

jak recznie do wkleje Ctrl+v to sie wklei, programowo jednak nie potrafie na zaden sposob, pomozecie?

0

Kiedyś znalazłem taki kod, jak poniżej "klepany" w c++ i przetłumaczylem do Delphi. Używałem tego w mnóstwie programów, w tym WinAPI do kopiowania tego co potrzebuje do schowka i nie było problemów.

procedure CopyTextToClipBoard(TextToCopy : string);
var
  ClipBoardH : HGLOBAL;
begin
  OpenClipboard(0);
  EmptyClipboard;
  ClipBoardH := GlobalAlloc(GMEM_MOVEABLE and GMEM_DDESHARE, Length(TextToCopy) + 1);
  StrCopy(GlobalLock(ClipBoardH), PChar(TextToCopy));
  GlobalUnlock(ClipBoardH);
  SetClipboardData(CF_TEXT, ClipBoardH);
  CloseClipboard;
end;

Natomiast symulowanie klawiszy żeby coś wkleić jest totalnym nieporozumieniem. Jeżeli chcesz wklejać do standardowej kontrolki edycyjnej, to wyślij do niej po prostu komunikat WM_PASTE. Też nie powinno być problemów. Jedynie - o ile wiem, to jeżeli masz jakiś program, który monitoruje schowek i nie oddaje tak jak, to należy zrobić (i opisano na MSDN przy okazji opisu komunikatu WM_DRAWCLIPBOARD) kontroli po przechwyceniu zawartości schowka, to może są jakieś "cyrki". Ale jeśli nie, to wedle mojej wiedzy nie powinno nic sprawiać problemów z wklejeniem zawartości schowka czy skopiowaniem do niego. Chyba, że w tle działa Tobie jakiś dziwny malware, którego zadaniem jest celowe czyszczenie schowka co chwilę.

0

Skoro @olesio podał ładnie przykład z wykorzystaniem WinAPI, to ja dodatkowo polecę odpowiednik z obiektówki (z VCL);

librato3 napisał(a)

i teraz chcialbym owy tekst przypisac programowalnie do kontrolki Edit1.Text.
Nie potrafie tego zrobic.

Klasa TCustomEdit ma taką metodę, jak PasteFromClipboard, która służy do wklejania tekstowej zawartości schowka do komponentu; A pomijając już komponenty, w module Vcl.Clipbrd istnieje klasa TClipboard, którą także można wykorzystać do różnych operacji na systemowym schowku.

0
PasteFromClipboard

niestety nie dziala.

Jak juz wspomnialem zastosowalem unit ClipBoard i tez schowek pusty.

Symulacja kopiowania jest do tego ze kopiujemy tekst z innego 'okna', jednym slowem kopiuje sie jakos/gdzies, tylko problem z wklejeniem....

0

A po tym symulowanym skopiowaniu do schowka próbowałeś wkleić to do notatnika otwierając jakiś plik txt i wciskając na klawiaturze CTRL+V? Bo jednak stwierdzenie tekst jest niby w schowku, nie sugeruje abyś miał pewność czy on tam jest

0

Może nie napisalem jasno faktycznie.

Po symulacji kopiowania, moge tekst wklejac recznie CTRL V, albo myszka PPM > Wklej.

Wiec w teorii w schowku gdzies jest.

jednak metody typu PasteFromClipboard, czy tez sam obiekt Clipboard (astext itp), nie dzialaja - pusty schowek wg nich.

0

Jeżeli w Schowku nie byłoby obiektu typu CF_TEXT, czyli zwykłego tekstu. To pewnie nie wkleił by się normalnie do Notatnika. Nie wiem gdzie w nowszych systemach siedzi wygodny podgląd Schowka. Ale programista może sobie poradzic po swojemu. Na szybko machnąc coś, co monitoruje schowek poprzez choćby obsługę WM_DRAWCLIPBOARD. I zobaczyć co trafia do Schowka. A jeżeli dane do skopiowania podchodzą z obcej aplikacji. A są zawarte w jakiejś standardowej kontrolce edycyjnej. To wyślij do niej komunikat WM_COPY. I otrzymasz w Schowku to, co można skopiować. Symulacja klawiszy jest bez sensu, jeżeli są to standardowe kontrolki edycyjne, którym nikt nie kazał olewać takie komunikaty.

0

A jak jest to pole edycjne w kontrolki WebBrowser?

0

znalazłem rozwiązanie, logicznie może się nie trzyma kupy, ale działa:

begin
  Clipboard.Clear;

  Application.ProcessMessages;

  keybd_event(VK_CONTROL, MapVirtualKey(VK_CONTROL, 0), 0, 0);
  keybd_event(Ord('A'), MapVirtualKey(Ord('A'), 0), 0, 0);
  keybd_event(Ord('A'), MapVirtualKey(Ord('A'), 0), KEYEVENTF_KEYUP, 0);
  keybd_event(VK_CONTROL, MapVirtualKey(VK_CONTROL, 0), KEYEVENTF_KEYUP, 0);

  keybd_event(VK_CONTROL, MapVirtualKey(VK_CONTROL, 0), 0, 0);
  keybd_event(Ord('C'), MapVirtualKey(Ord('C'), 0), 0, 0);
  keybd_event(Ord('C'), MapVirtualKey(Ord('C'), 0), KEYEVENTF_KEYUP, 0);
  keybd_event(VK_CONTROL, MapVirtualKey(VK_CONTROL, 0), KEYEVENTF_KEYUP, 0);

  Application.ProcessMessages;
end; 

bez

Application.ProcessMessages;

nie działało - dziwne.

Powyższy kod jest rozwiązaniem, może się komuś przyda.

1

Od tego trzeba było zacząć wątek. Najważnejsza informacja. Do tego też pewnie są metody by skopiowac z WebBrowsera. Natomiast używanie przestarzałego keybd_event zamiast zalecanego SendInput, nawet jeśli fartownie działa = daleko Cię nie zaprowadzi.

1 użytkowników online, w tym zalogowanych: 0, gości: 1