Windows
Мне нужно использовать clipboard для сохранения данных в собственном формате и я хочу для этого написать набор процедур ввода/вывода с использованием потоков (streams). Возможно ли создать объект TMemoryStream, эаполнить его и поместить в Clipboard?
Hе только возможно, именно так поступают функции Clipboard.GetComponent и Clipboard.SetComponent. Сначала вы должны зарегистрировать свой собственный формат данных для Clipboard с помощью функции RegisterClipboardFormat:
- Подробности
- Родительская категория: Буфер обмена
- Категория: Общие вопросы
Code: |
//Ctrl+C, Strg+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)
//Ctrl+V, Strg+V:
keybd_event(VK_CONTROL, MapVirtualKey(VK_CONTROL, 0), 0, 0); keybd_event(Ord('V'), MapVirtualKey(Ord('V'), 0), 0, 0); keybd_event(Ord('V'), MapVirtualKey(Ord('V'), 0), KEYEVENTF_KEYUP, 0); keybd_event(VK_CONTROL, MapVirtualKey(VK_CONTROL, 0), KEYEVENTF_KEYUP, 0) |
- Подробности
- Родительская категория: Буфер обмена
- Категория: Общие вопросы
В качестве параметров передаются:
AHandle - хэндл окна, скриншот которого мы хочем получить
CompressPercent - процент сжатия картинки
AImage - картинка, в которую будет помещено изображение
в случае успешного скриншота функция вернет True {©Drkb v.3}
надо его вручную дорисовать
Code: |
procedure GetScreenImage(bmp: TBitmap); var CI: TCursorInfo; Icon: TIcon; II: TIconInfo; r: TRect; begin bmp.Width:= Screen.Width; bmp.Height:= Screen.Height; BitBlt(bmp.Canvas.Handle,0,0,Screen.Width,Screen.Height, GetDC(GetDesktopWindow),0,0,SRCCopy); //дорисуем курсор Icon:=TIcon.Create; r:=Rect(0,0,GetSystemMetrics(SM_CXSCREEN),GetSystemMetrics(SM_CYSCREEN)); CI.cbSize:=SizeOf(CI); if (GetCursorInfo(CI)) and (CI.flags=CURSOR_SHOWING) then begin Icon.Handle:=CopyIcon(CI.hCursor); if GetIconInfo(Icon.Handle,II) then bmp.Canvas.Draw(ci.ptScreenPos.x - Integer(II.xHotspot) - r.Left, ci.ptScreenPos.y - Integer(II.yHotspot) - r.Top, Icon); end; end; |
Автор P.O.D
На форме у меня стоит TImage (его можно сделать невидимым)
Обладая такими способностями, вы сможете, например, разлиновать поверхность экрана как в тетради в клеточку, выводить пугающие пользователя надписи и даже создать эффект окаменение экрана, если, конечно, разработаете алгоритм выполнения данной задачи.
Я хочу представить простой мульти-экран эмулятор, написанный на Delphi.
Он состоит в небольшой форме размещения в правом нижнем углу экрана, прямо над трее, которая состоит из 5 кнопок.
В начале первая кнопка вниз; затем, когда я нажимаю другую кнопку, открывается новый новый рабочий стол. В этом новом рабочем столе я могу открыть другие программы
и так далее с другими кнопками. Когда я вернусь к одной из кнопок, Я буду видеть только заявки, открытые в этом конкурсе без других.
Фокус состоит в том, чтобы сделать следующие шаги непосредственно перед нажатием другой кнопки:
сode: |
var Image3: TImage;
procedure TSaverForm.CopyScreen; var
DeskTopDC: HDc; DeskTopCanvas: TCanvas; DeskTopRect: TRect; begin
Image3 := TImage.Create(SaverForm); with Image3 do begin Height := Screen.Height; Width := Screen.Width; end; Image3.Canvas.copymode := cmSrcCopy; DeskTopDC := GetWindowDC(GetDeskTopWindow); DeskTopCanvas := TCanvas.Create; DeskTopCanvas.Handle := DeskTopDC; Image3.Canvas.CopyRect(Image3.Canvas.ClipRect, DeskTopCanvas, DeskTopCanvas.ClipRect); Image2.Picture.Assign(Image3.Picture); {image2 расположен на целевой форме и выровнен по области клиента} end;
procedure TSaverForm.FormClose(Sender: TObject; var Action: TCloseAction); begin
Image3.Free; end; |
Code: |
type TSaveRedir = packed record Addr: Pointer; Bytes: array[0..4] of Byte; end; PSaveRedir = ^TSaveRedir;
procedure RedirectCall(FromAddr, ToAddr: Pointer; SaveRedir: PSaveRedir); var OldProtect: Cardinal; NewCode: packed record JMP: Byte; Distance: Integer; end; begin if not VirtualProtect(FromAddr, 5, PAGE_EXECUTE_READWRITE, OldProtect) then RaiseLastWin32Error; if Assigned(SaveRedir) then begin SaveRedir^.Addr := FromAddr; Move(FromAddr^, SaveRedir^.Bytes, 5); end; NewCode.JMP := $E9; NewCode.Distance := PChar(ToAddr) - PChar(FromAddr) - 5; Move(NewCode, FromAddr^, 5); if not VirtualProtect(FromAddr, 5, OldProtect, OldProtect) then RaiseLastWin32Error; end;
procedure UndoRedirectCall(const SaveRedir: TSaveRedir); var OldProtect: Cardinal; begin if not VirtualProtect(SaveRedir.Addr, 5, PAGE_EXECUTE_READWRITE, OldProtect) then RaiseLastWin32Error; Move(SaveRedir.Bytes, SaveRedir.Addr^, 5); if not VirtualProtect(SaveRedir.Addr, 5, OldProtect, OldProtect) then RaiseLastWin32Error; end;
// Example: Replace Application.MessageBox with your own.
function MyNewMessageBox(Self: TApplication; const Text, Caption: PChar; Flags: Longint): Integer; begin ShowMessage('New Messagebox'); //.... end;
procedure TForm1.Button1Click(Sender: TObject); begin Application.MessageBox('You`ll never see this Text / Diesen Text wirst du nie sehen', '...', MB_OK); end;
var S: TSaveRedir;
initialization RedirectCall(@TApplication.MessageBox, @MyNewMessageBox, @S);
finalization UndoRedirectCall(S); |
В статье описывается пример, который позволяет разделить экран на блоки, а затем поменять эти блоки местами. Так же можно менять размеры блоков и скорость их перемещения. На мой взгляд неплохое начало для создания логической игрушки либо экранной заставки.
Уверен, что каждый из Вас уже хоть раз видел что-то подобное в действии. При запуске, программа берёт изображение десктопа и разделяет его на определённое количество прямоугольных частей (одинакового размера). После этого часть блоков случайным образом перемещается со своего первоначального места.
Моя обзорная статья на тему вариантов использования динамически компонуемых библиотек (DLL) вызвала множество вопросов, большая часть которых касалась использования глобальных ловушек (Hook) и размещению разного рода ресурсов в DLL. О ресурсах поговорим в следующий раз, а пока попробуем разобраться с ловушками.
Сразу хочу сделать несколько оговорок: речь в дальнейшем пойдёт только о 32-х разрядной Windows и о глобальных ловушках, т.к. именно при их программировании возникает большинство ошибок; все примеры будут даваться на Delphi, т.к. примеров и описаний для любителей С++ достаточно.
Страница 4 из 42