unit main; //{$DEFINE DEBUG} interface uses Windows, ActnList, AppEvnts, Classes, ComCtrls, Controls, Dialogs, ExtCtrls, Forms, Graphics, Menus, Messages, StdCtrls, SysUtils, my_settingfile, my_monitor, ImgList; type T_MyBounds = record Left, Top, Width, Height: Integer; end; type T_DispInfo = record //表示用 //カーソル位置のカラー情報 iRed, iGreen, iBlue: Integer; //RGB用 clColor, clColorRef: TColor; //HTML用、COLORREF用 ptMousePos, //スクリーン座標、モニター座標 ptClientPos, //クライアント座標の原点, ptUserPos: TPoint; //任意座標の原点 hWinHandle: HWND; sWinClass: String; sWinText: WideString; szWindowSize, szClientSize: T_MyBounds; rcWinRect: TRect; sExeName: WideString; end; type TApp_LenZoom = class(TForm) ActionList_Main: TActionList; actZoom_1: TAction; actZoom_2: TAction; actZoom_3: TAction; actZoom_4: TAction; actZoom_6: TAction; actZoom_8: TAction; actZoom_10: TAction; actZoom_12: TAction; actZoom_16: TAction; actZoom_20: TAction; actZoom_Up: TAction; actZoom_Down: TAction; actGrid_Disp: TAction; actGrid_Gray: TAction; actGrid_Invert: TAction; actGrid_Transparent: TAction; actGrid_SelColor: TAction; actGrid_SubBlue: TAction; actGrid_SelSubColor: TAction; actColor_RGB: TAction; actColor_HTML: TAction; actColor_COLORREF: TAction; actColor_InfoOnOff: TAction; actPos_Screen: TAction; actPos_Client: TAction; actPos_User: TAction; actPos_UserPosSet: TAction; actPos_InfoOnOff: TAction; actWinInfo_Handle: TAction; actWinInfo_ClassName: TAction; actWinInfo_Text: TAction; actWinInfo_WindowSize: TAction; actWinInfo_ClientSize: TAction; actWinInfo_Rect: TAction; actWinInfo_ExeName: TAction; actWinInfo_InfoOnOff: TAction; actCopy_Picture: TAction; actCopy_ColorHTML: TAction; actCopy_ColorRGB: TAction; actCopy_ColorCOLORREF: TAction; actCopy_PosScreen: TAction; actCopy_PosClient: TAction; actCopy_PosUser: TAction; actCopy_WInfoHandle: TAction; actCopy_WInfoClassName: TAction; actCopy_WInfoText: TAction; actCopy_WInfoWindowSize: TAction; actCopy_WInfoClientSize: TAction; actCopy_WInfoRect: TAction; actCopy_WInfoExeName: TAction; actCapture_Pause: TAction; actCapture_Lupe: TAction; actCapture_Fixed: TAction; actCapture_Disp_x1: TAction; actOpt_StayOnTop: TAction; actOpt_BigFont: TAction; actOpt_NoSelfCapture: TAction; actOpt_SmoothCapture: TAction; actMenu_Main: TAction; actMove_Monitor: TAction; actMove_Left: TAction; actMove_Right: TAction; actMove_Up: TAction; actMove_Down: TAction; actFile_Minimize: TAction; actFile_Exit: TAction; actHelp: TAction; mnuMain: TPopupMenu; mniZoom: TMenuItem; mniZoom_1: TMenuItem; mniZoom_2: TMenuItem; mniZoom_3: TMenuItem; mniZoom_4: TMenuItem; mniZoom_6: TMenuItem; mniZoom_8: TMenuItem; mniZoom_10: TMenuItem; mniZoom_12: TMenuItem; mniZoom_16: TMenuItem; mniZoom_20: TMenuItem; mniGrid: TMenuItem; mniGrid_Disp: TMenuItem; mniGrid_LineGrid: TMenuItem; mniGrid_Gray: TMenuItem; mniGrid_Invert: TMenuItem; mniGrid_Transparent: TMenuItem; mniGrid_SelColor: TMenuItem; mniGrid_LineSubGrid: TMenuItem; mniGrid_SubBlue: TMenuItem; mniGrid_SelSubColor: TMenuItem; mniMain_Line1: TMenuItem; mniColor: TMenuItem; mniColor_RGB: TMenuItem; mniColor_HTML: TMenuItem; mniColor_ColorRef: TMenuItem; mniColor_Line1: TMenuItem; mniColor_InfoOnOff: TMenuItem; mniPos: TMenuItem; mniPos_Screen: TMenuItem; mniPos_Client: TMenuItem; mniPos_User: TMenuItem; mniPos_Line1: TMenuItem; mniPos_InfoOnOff: TMenuItem; mniWinInfo: TMenuItem; mniWinInfo_Handle: TMenuItem; mniWinInfo_ClassName: TMenuItem; mniWinInfo_Text: TMenuItem; mniWinInfo_WindowSize: TMenuItem; mniWinInfo_ClientSize: TMenuItem; mniWinInfo_Rect: TMenuItem; mniWinInfo_ExeName: TMenuItem; mniWinInfo_Line1: TMenuItem; mniWinInfo_InfoOnOff: TMenuItem; mniMain_Line2: TMenuItem; mniCopy: TMenuItem; mniCopy_Picture: TMenuItem; mniCopy_Line1: TMenuItem; mniCopy_ColorRGB: TMenuItem; mniCopy_ColorHTML: TMenuItem; mniCopy_ColorColorRef: TMenuItem; mniCopy_Line2: TMenuItem; mniCopy_PosScreen: TMenuItem; mniCopy_PosClient: TMenuItem; mniCopy_PosUser: TMenuItem; mniCopy_Line3: TMenuItem; mniCopy_WInfoHandle: TMenuItem; mniCopy_WInfoClassName: TMenuItem; mniCopy_WInfoText: TMenuItem; mniCopy_WInfoWindowSize: TMenuItem; mniCopy_WInfoClientSize: TMenuItem; mniCopy_WInfoRect: TMenuItem; mniCopy_WInfoExeName: TMenuItem; mniCapture: TMenuItem; mniCapture_Pause: TMenuItem; mniCapture_Line1: TMenuItem; mniCapture_Lupe: TMenuItem; mniCapture_Fixed: TMenuItem; mniOpt: TMenuItem; mniOpt_StayOnTop: TMenuItem; mniOpt_FontSize: TMenuItem; mniOpt_NoSelfCapture: TMenuItem; mniOpt_SmoothCapture: TMenuItem; mniMain_Line3: TMenuItem; mniHelp_VersionInfo: TMenuItem; mniFile_Minimize: TMenuItem; mniMain_Line4: TMenuItem; mniFile_Exit: TMenuItem; Timer_Main: TTimer; Timer_Infomation: TTimer; ColorDialog: TColorDialog; ApplicationEvents1: TApplicationEvents; actCapture_Update: TAction; ImageList_Icon: TImageList; procedure FormCreate (Sender: TObject); procedure FormDestroy (Sender: TObject); procedure FormResize (Sender: TObject); procedure FormPaint (Sender: TObject); procedure FormDblClick (Sender: TObject); procedure FormKeyDown (Sender: TObject; var Key: Word; Shift: TShiftState); procedure FormKeyUp (Sender: TObject; var Key: Word; Shift: TShiftState); procedure FormMouseUp (Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Integer); procedure FormMouseMove (Sender: TObject; Shift: TShiftState; X, Y: Integer); procedure FormMouseDown (Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Integer); procedure FormMouseWheelUp (Sender: TObject; Shift: TShiftState; MousePos: TPoint; var Handled: Boolean); procedure FormMouseWheelDown(Sender: TObject; Shift: TShiftState; MousePos: TPoint; var Handled: Boolean); procedure actNop (Sender: TObject); procedure actZoomExecute (Sender: TObject); procedure actZoom_UpExecute (Sender: TObject); procedure actZoom_DownExecute (Sender: TObject); procedure actGrid_DispExecute (Sender: TObject); procedure actGrid_SubBlueExecute (Sender: TObject); procedure actGrid_ColorExecute (Sender: TObject); procedure actGrid_SelColorExecute (Sender: TObject); procedure actColor_InfoOnOffExecute (Sender: TObject); procedure actPos_UserPosSetExecute (Sender: TObject); procedure actPos_InfoOnOffExecute (Sender: TObject); procedure actWinInfo_InfoOnOffExecute (Sender: TObject); procedure actMenu_MainExecute (Sender: TObject); procedure actCopy_PictureExecute (Sender: TObject); procedure actCopy_TextExecute (Sender: TObject); procedure actOpt_StayOnTopExecute (Sender: TObject); procedure actOpt_BigFontExecute (Sender: TObject); procedure actOpt_NoSelfCaptureExecute (Sender: TObject); procedure actCapture_PauseExecute (Sender: TObject); procedure actCapture_LupeExecute (Sender: TObject); procedure actCapture_FixedExecute (Sender: TObject); procedure actOpt_SmoothCaptureExecute (Sender: TObject); procedure actCapture_UpdateExecute (Sender: TObject); procedure actMove_MonitorExecute (Sender: TObject); procedure actMove_LeftExecute (Sender: TObject); procedure actFile_MinimizeExecute (Sender: TObject); procedure actFile_ExitExecute (Sender: TObject); procedure actHelpExecute (Sender: TObject); procedure Timer_MainTimer (Sender: TObject); procedure Timer_InfomationTimer (Sender: TObject); procedure ApplicationEvents1Activate (Sender: TObject); procedure ApplicationEvents1Deactivate(Sender: TObject); procedure ApplicationEvents1ShortCut (var Msg: TWMKey; var Handled: Boolean); procedure ApplicationEvents1Message (var Msg: tagMSG; var Handled: Boolean); private { Private 宣言 } F_bThrough: Boolean; //無用なイベントを捨てる F_bThroughTimer: Boolean; //タイマーイベントで処理し切れなかったイベントを捨てるため F_iZoom, //倍率 F_iZoomIndex, //選択されている倍率メニューのインデックス F_iZoomBak: Integer; //一時停止、定点キャプチャ時にShiftを押したとき一時的に倍率を1倍にするために必要 F_clGridColor, //グリッドの色 F_clSubGridColor: TColor; //サブグリッドの色 F_pmPenMode: TPenMode; //反転色、半透明色があるために必要 F_bmpDesktop, //一時停止時にデスクトップをキャッシュ F_bmpDraw: TBitmap; //最終的にこれがSelf.Canvasにコピーされる F_szDesktop, //拡大元の大きさ F_szZoom: T_MyBounds; //拡大後の大きさ。二つともにLeft,Topの値は中心を示すために使用していることに注意 F_iHGrid, F_iVGrid: Integer; //グリッドの数 //情報表示部 F_rcInfo: TRect; //情報表示領域 F_sInfomation: WideString; //1行表示 F_ptColorPos: TPoint; //色情報を得る為の位置 カーソルボックスもこの値を利用している F_iFontHeight: Integer; //文字の高さ=一行の高さ F_iFontWidth: Integer; F_iInfoLeft: Integer; //ステータスアイコン表示のLeft値 F_iVLine: Integer; //情報表示の項目名と情報との境に引くラインの横の位置 F_iPassTime: DWORD; //前回キャプチャからの経過時間 F_ptGesture: TPoint; //マウスジェスチャー F_rDispInfo: T_DispInfo; //表示用の情報 //一時停止時にキャプチャポジションを移動させる F_bIsMoving: Boolean; //フォームをつかんでいるか F_ptMvClientMousePos, //マウスポインタにキャプチャポインタを移動させるため F_ptMvMousePos: TPoint; //フォームをつかんでキャプチャポインタを動かすため F_iMonitorNum: Integer; //前回カーソルがあったモニターの番号(モニターの範囲外にカーソルポイントが移動しないために) procedure F_Capture_KeyDown; procedure F_Capture_KeyUp; procedure F_Capture_MovePoint(ptPos: TPoint); procedure F_Zoom_UpDown(Sender: TObject); procedure F_SetPoint; function F_GetPointShift: Integer; procedure F_PushInfomation(sText: WideString); function F_GetWindow(ptPos: TPoint): HWND; function F_GetDispFmt(iIndex: Integer): String; function F_GetCopyFmt(iIndex: Integer): String; function F_GetCopyZoomGrid: Boolean; procedure F_PutInfo(Sender: TObject; var iInfoTop: Integer); function F_GetDrawFont: TFont; procedure F_MouseResize(X, Y: Integer; bSizing: Boolean); procedure F_ExecuteCmd(iCmd: Word); function F_LoadBin: Boolean; procedure F_SaveBin; procedure WMQueryEndSession(var Msg: TWMQueryEndSession); message WM_QUERYENDSESSION; procedure WMDisplayChange (var Msg: TMessage); message WM_DISPLAYCHANGE; procedure WMSysCommand (var Msg: TWMSysCommand); message WM_SYSCOMMAND; procedure WMEraseBkGnd (var Msg: TMessage); message WM_ERASEBKGND; protected // procedure CreateParams(var Params: TCreateParams); override; public { Public 宣言 } procedure DrawNow; procedure MoveCursorToPoint(Sender: TObject); function GetMonitorItem(ptPos: TPoint): TMyMonitorItem; property CopyFmt[iIndex: Integer]: String read F_GetCopyFmt;// write F_SetCopyFmt; property DrawFont: TFont read F_GetDrawFont; end; //------------------------------------------------------------------------------ var App_LenZoom: TApp_LenZoom; implementation uses {$IFDEF DEBUG} myDebug, {$ENDIF} Clipbrd, general; {$R *.dfm} const CAPTUREBLT = $40000000; //レイヤーウィンドウも含めたキャプチャを行うフラグ const //マウスを動かしていない時であっても画面更新を行う時間(ミリ秒) FciCapture_RefleshTime = 1000; const FciMINGRID = 4; //グリッドを引く最低倍率 FciMINSIZE = 50; //描画領域の最小の高さ&フォームの幅 //タスクバーのメニュー拡張 lciMENU_LINE = 100; lciMENU_MOVEMONITOR = 201; //フォーマットの初期値 const G_ciFMTZOOM = 0; G_ciFMTCOLOR_RGB = 1; G_ciFMTCOLOR_HTML = 2; G_ciFMTCOLOR_COLORREF = 3; G_ciFMTPOS_SCREEN = 4; G_ciFMTPOS_CLIENT = 5; G_ciFMTPOS_USER = 6; G_ciFMTWININFO_HANDLE = 7; G_ciFMTWININFO_CLASSNAME = 8; G_ciFMTWININFO_TEXT = 9; G_ciFMTWININFO_WINDOWSIZE = 10; G_ciFMTWININFO_CLIENTSIZE = 11; G_ciFMTWININFO_RECT = 12; G_ciFMTWININFO_EXENAME = 13; G_ciFMTCOUNT = G_ciFMTWININFO_EXENAME; const G_csDISPFMT: array[0..G_ciFMTCOUNT] of String = ( '%2d倍', //6倍 'RGB R=%-3d G=%-3d B=%-3d', //RGB 'HTML %s', //HTML 'COLORREF %1:s %0:d', //引数は二つ。順番を入れ替えている 'スクリーン X=%d Y=%d', // 'クライアント X=%d Y=%d (%d,%d)', //()内はクライアントの原点 '任意 X=%d Y=%d (%d,%d)', //()内はユーザー指定の原点 'ハンドル %s %d', //引数は二つ。 'クラス名 %s', // 'テキスト %s', // 'Wサイズ L=%2:d T=%3:d W=%0:d H=%1:d', //Left, Top, Width, Height(親ウィンドウのクライアント座標) 'Cサイズ W=%d H=%d', //Width, Height(Left, Topは必ず0なので省略) 'Rect L=%d T=%d R=%d B=%d', //Left, Top, Right, Bottom '実行ファイル %s' //実行ファイル名 ); lcsFMT_COPY = '%sをコピー %s'; //コピーしたときのメッセージ lcsMARK_PICTURE = 'ズーム画像'; //ズーム画像をコピーしたときに付加するメッセージ lcsMARK_FIXED = '(%d,%d) '; //定点キャプチャ const G_csCOPYFMT: array[0..G_ciFMTCOUNT, 0..1] of String = ( ('11', '01'), //画像 ('%d %d %d', '%x %x %x'), //RGB ('%.6x', '%d'), //HTML ('%d', '%x'), //COLORREF ('%d, %d', '(%d, %d)'), //Screen ('%d, %d', '(%d, %d)'), //Client ('%d, %d', '(%d, %d)'), //User ('%d', '%.8x'), //Handle ('%s', '"%s"'), //ClassName ('%s', '"%s"'), //Text ('%d, %d, %d, %d', '(%d, %d, %d, %d)'), //Window Size ('%d, %d', '(%d, %d)'), //Client Size ('%d, %d, %d, %d', '(%d, %d, %d, %d)'), //Rect ('%s', '%1:s') //Exe Name ); procedure TApp_LenZoom.WMEraseBkGnd(var Msg: TMessage); begin Msg.Result := 0; end; //============================================================================== //モニター function TApp_LenZoom.GetMonitorItem(ptPos: TPoint): TMyMonitorItem; begin Result := MyMonitors[MyMonitors.MonitorIndex(ptPos)]; end; //ディスプレイ設定が変わった procedure TApp_LenZoom.WMDisplayChange(var Msg: TMessage); begin MyMonitors.Reflesh; //モニター内に納まるようなSetBouds //フォームスタイルが標準のツールバーだと何もしなくてもモニター内に収まるがbsNoneだと自前でやらないとならない MyMonitors.SetBounds(Self, Left, Top, Width, Height); end; procedure TApp_LenZoom.WMSysCommand(var Msg: TWMSysCommand); begin //myDebug.gpcDebugAdd('WMSysCommand', Msg.CmdType); case Msg.CmdType of SC_MAXIMIZE: begin end; 61490: begin //タイトルバーのダブルクリック end; { 61587: begin actMenu_MainExecute(nil); end; } else begin inherited; end; end; end; //OS終了メッセージ procedure TApp_LenZoom.WMQueryEndSession(var Msg: TWMQueryEndSession); begin //http://www.wwlnk.com/boheme/delphi/tips/tec0690.htm // Close; FormDestroy(Self); Msg.Result := 1; end; //タスクバーのメニュー拡張 procedure TApp_LenZoom.ApplicationEvents1Message(var Msg: tagMSG; var Handled: Boolean); begin if (Msg.hwnd = Application.Handle) then begin if (Msg.message = WM_SYSCOMMAND) then begin case Msg.wParam of lciMENU_MOVEMONITOR: actMove_MonitorExecute(nil); end; end; end; end; procedure TApp_LenZoom.FormCreate(Sender: TObject); var lh_Menu: HMENU; l_Monitor: TMyMonitorItem; begin {$IFDEF DEBUG} myDebug.gpcMessageModeSet(True); {$ENDIF} l_Monitor := GetMonitorItem(gfnptMousePosGet); SetBounds(l_Monitor.Left + 75, l_Monitor.Top + 75, Width, Height); Caption := Format('%s:Ver %s', [gfnsProductNameGet, gfnsFileVersionGet]); F_bThrough := False; F_bIsMoving := False; F_ptGesture := Point(-1, -1); F_iMonitorNum := 0; F_iZoomIndex := mniZoom.Tag; F_iZoom := mniZoom.Items[F_iZoomIndex].Tag; F_iZoomBak := -1; F_pmPenMode := pmCopy; F_clGridColor := actGrid_Gray.Tag; F_clSubGridColor := actGrid_SubBlue.Tag; //最大化メニューを削除。 lh_Menu := GetSystemMenu(Self.Handle, False); DeleteMenu (lh_Menu, SC_MAXIMIZE, MF_BYCOMMAND); DrawMenuBar(lh_Menu); //タスクバーのメニュー。モニター間移動を挿入 lh_Menu := GetSystemMenu(Application.Handle, False); InsertMenu(lh_Menu, 0, MF_BYPOSITION or MF_SEPARATOR, 0, nil); InsertMenu(lh_Menu, 0, MF_BYPOSITION, lciMENU_MOVEMONITOR, PChar(actMove_Monitor.Caption)); DrawMenuBar(lh_Menu); //一時停止時の画面キャプチャ F_bmpDesktop := TBitmap.Create; F_bmpDesktop.Canvas.Brush.Color := clBlack; F_bmpDesktop.Width := MyMonitors.ScreenWidth; F_bmpDesktop.Height := MyMonitors.ScreenHeight; F_bmpDraw := TBitmap.Create; // F_bmpDraw.HandleType := bmDIB; with F_bmpDraw.Canvas do begin Font := Self.Font; Font.Color := clWindowText; end; //設定情報読み込み if not(F_LoadBin) then begin actOpt_BigFontExecute(actOpt_BigFont); end; if not(gfnbIsOSUpper2000) then begin //2000未満はAlphaBlendに非対応 actCapture_Lupe.Checked := False; actCapture_Lupe.Enabled := False; actCapture_Lupe.Visible := False; mniCapture_Fixed.RadioItem := False; actOpt_NoSelfCapture.Enabled := False; actOpt_NoSelfCapture.Visible := False; Self.AlphaBlend := False; end; if not(G_bIsNtOS) then begin //9x系では実行ファイル名を取得できない actWinInfo_ExeName.Checked := False; actWinInfo_ExeName.Enabled := False; actWinInfo_ExeName.Visible := False; actCopy_WInfoExeName.Enabled := False; actCopy_WInfoExeName.Visible := False; end; Tag := 1; FormResize(nil); Timer_Main.Enabled := True; Show; //これがないとプライマリモニターの外に表示されてしまうことがある、不可解。 if not(actOpt_StayOnTop.Checked) then begin SetWindowPos(Self.Handle, HWND_TOPMOST, 0, 0, 0, 0, SWP_NOMOVE or SWP_NOSIZE); SetWindowPos(Self.Handle, HWND_NOTOPMOST, 0, 0, 0, 0, SWP_NOMOVE or SWP_NOSIZE); end; end; //破棄 procedure TApp_LenZoom.FormDestroy(Sender: TObject); begin Tag := 0; if (IsZoomed(Handle)) or (IsIconic(Handle)) then begin ShowWindow(Handle, SW_NORMAL); end; F_SaveBin; //↓はこの位置でないとエラーになる F_bmpDesktop.Free; F_bmpDraw.Free; end; //アクティブでなくなった //フォームへ描画 procedure TApp_LenZoom.FormPaint(Sender: TObject); begin //拡大画像の描画。これがメイン。 Windows.BitBlt(Canvas.Handle, 0, 0, ClientWidth, ClientHeight, F_bmpDraw.Canvas.Handle, 0, 0, SRCCOPY); if (GetActiveWindow = Self.Handle) then begin Canvas.Pen.Color := clActiveCaption; end else begin Canvas.Pen.Color := clInActiveCaption; end; Canvas.Pen.Mode := pmCopy; Canvas.MoveTo(0, 0); Canvas.LineTo(0, ClientHeight -1); Canvas.LineTo(ClientWidth -1, ClientHeight -1); Canvas.LineTo(ClientWidth -1, 0); Canvas.LineTo(0, 0); end; //描画領域の変更 procedure TApp_LenZoom.FormResize(Sender: TObject); //ズーム領域調整関数 function lfnrc_RectMagni(const rcRect: TRect; const fMagni: Extended): TRect; begin Result := Rect(0, 0, gfniRoundUp(fMagni * gfniRectWidth(rcRect)), gfniRoundUp(fMagni * gfniRectHeight(rcRect))); end; //============================================================================ var li_ShiftColorPos: Integer; li_Height: Integer; lrc_Screen, lrc_Zoom: TRect; begin if (Tag = 0) then begin Exit; end else begin Tag := 0; end; //情報表示枠の高さをセット------------------------------------------------------ li_Height := 0; F_PutInfo(Sender, li_Height); ClientHeight := ClientHeight + (li_Height - gfniRectHeight(F_rcInfo)); if ((ClientHeight - li_Height) < FciMINSIZE) then begin ClientHeight := FciMINSIZE + li_Height + 2; //枠の分で+2 end; if (ClientWidth < FciMINSIZE) then begin ClientWidth := FciMINSIZE + 2; //枠の分で+2 end; with F_rcInfo do begin Right := ClientWidth; Bottom := ClientHeight; Top := Bottom - li_Height; end; //拡大のための領域のセット------------------------------------------------------ with F_bmpDraw do begin Width := Self.ClientWidth; Height := Self.ClientHeight; end; //拡大元の領域 := ズーム表示領域 / 倍率 lrc_Screen := lfnrc_RectMagni(Rect(0, 0, ClientWidth, F_rcInfo.Top), 1/F_iZoom); //(端数が出ないように調整された)拡大される領域 lrc_Zoom := lfnrc_RectMagni(lrc_Screen, F_iZoom); //拡大後の領域情報 with F_szZoom do begin Width := gfniRectWidth(lrc_Zoom); Height := gfniRectHeight(lrc_Zoom); //Left,Top は中心を示すことに注意 Left := gfniRound(Width / 2) -1; Top := gfniRound(Height / 2) -1; //グリッドの数 F_iHGrid := gfniRound(Width / F_iZoom); F_iVGrid := gfniRound(Height / F_iZoom); end; //拡大元の領域情報 with F_szDesktop do begin Width := gfniRectWidth(lrc_Screen); Height := gfniRectHeight(lrc_Screen); //Left,Top は中心を示すことに注意 Left := gfniRound(Width / 2) -1; Top := gfniRound(Height / 2) -1; end; //グリッドを引くか引かないかでカラーの値を取る位置が1ドットずれる if (F_GetPointShift > 1) then begin li_ShiftColorPos := 1; //グリッドあり、1ドット右下にずらす end else begin li_ShiftColorPos := 0; //グリッドなし、そのまま end; //カラー取得位置 F_ptColorPos := Point( (gfniRound(F_iHGrid / 2) -1) * F_iZoom + li_ShiftColorPos, //X (gfniRound(F_iVGrid / 2) -1) * F_iZoom + li_ShiftColorPos //Y ); Tag := 1; Timer_InfomationTimer(nil); DrawNow; end; //描画スタート・今すぐ描画 procedure TApp_LenZoom.DrawNow; begin if (Tag <> 0) then begin F_iPassTime := 0; //すぐに再描画させたい為に間隔判定用のフラグを0にセットする Timer_MainTimer(Timer_Main); Timer_Main.Tag := 100; //マウスが動いていなくても画面更新を行う時間を一度だけ短くする。 end; end; //------------------------------------------------------------------------------ //マウスカーソルのカーソルポイントを示すボックスを描く時の枠の幅を返す //倍率選択とグリッド色選択で使用する function TApp_LenZoom.F_GetPointShift: Integer; begin if (actGrid_Disp.Checked) and (F_iZoom >= FciMINGRID) then begin Result := 2; //グリッドの線を避けるため1ドット足して2 end else begin //※グリッドとカーソルボックスの線の引き方は違っている Result := 1; //グリッド表示がないので1ですむ end; end; //倍率選択 procedure TApp_LenZoom.actZoomExecute(Sender: TObject); begin with (Sender as TAction) do begin Checked := True; F_iZoom := Abs(Tag); F_iZoomIndex := (Self.FindComponent('mni' + Copy(Name, 4, Length(Name) -3)) as TMenuItem).MenuIndex; end; FormResize(nil); end; //倍率の上下 procedure TApp_LenZoom.F_Zoom_UpDown(Sender: TObject); var li_Zoom: Integer; begin if (F_iZoomBak > 0) then Exit; if (Sender = actZoom_Up) then begin li_Zoom := 1; end else if (Sender = actZoom_Down) then begin li_Zoom := -1; end else begin Exit; end; if ((li_Zoom = -1) and (F_iZoomIndex <= 0)) //倍率が既に最低の時 or ((li_Zoom = 1) and (F_iZoomIndex >= mniZoom.Count -1)) //倍率が既に最高の時 then begin Exit; end; actZoomExecute(mniZoom.Items[gfniNumLimit(F_iZoomIndex + li_Zoom, 0, mniZoom.Count -1)].Action); end; procedure TApp_LenZoom.actZoom_UpExecute(Sender: TObject); begin F_Zoom_UpDown(actZoom_Up); end; procedure TApp_LenZoom.actZoom_DownExecute(Sender: TObject); begin F_Zoom_UpDown(actZoom_Down); end; //ホイールで倍率の上下 procedure TApp_LenZoom.FormMouseWheelDown(Sender: TObject; Shift: TShiftState; MousePos: TPoint; var Handled: Boolean); begin //F_bThroughがTrueなら処理しきれないイベントを捨てる if (F_bThrough) then Exit; F_bThrough := True; if (ssAlt in Shift) then begin //カーソル移動→ actMove_LeftExecute(actMove_Right); end else if (ssCtrl in Shift) then begin //カーソル移動↓ actMove_LeftExecute(actMove_Down); end else begin //倍率→低 F_Zoom_UpDown(actZoom_Down); end; Handled := True; Application.ProcessMessages; //溜まってるイベントを捨てる F_bThrough := False; end; procedure TApp_LenZoom.FormMouseWheelUp(Sender: TObject; Shift: TShiftState; MousePos: TPoint; var Handled: Boolean); begin //F_bThroughがTrueなら処理しきれないイベントを捨てる if (F_bThrough) then Exit; F_bThrough := True; if (ssAlt in Shift) then begin //カーソル移動← actMove_LeftExecute(actMove_Left); end else if (ssCtrl in Shift) then begin //カーソル移動↑ actMove_LeftExecute(actMove_Up); end else begin //倍率→高 F_Zoom_UpDown(actZoom_Up); end; Handled := True; Application.ProcessMessages; //溜まってるキューを捨てる F_bThrough := False; end; //------------------------------------------------------------------------------ //グリッド procedure TApp_LenZoom.actGrid_DispExecute(Sender: TObject); //グリッド表示ON/OFF begin actGrid_Disp.Checked := not(actGrid_Disp.Checked); FormResize(nil); DrawNow; end; procedure TApp_LenZoom.actGrid_ColorExecute(Sender: TObject); //グリッド色、灰、反転、半透明 begin TAction(Sender).Checked := True; F_clGridColor := TComponent(Sender).Tag; if (Sender = actGrid_Invert) then begin //反転色 F_pmPenMode := pmNot; end else if (Sender = actGrid_Transparent) then begin F_pmPenMode := pmMask; end else begin F_pmPenMode := pmCopy; end; DrawNow; end; //サブグリッド色、青 procedure TApp_LenZoom.actGrid_SubBlueExecute(Sender: TObject); begin TAction(Sender).Checked := True; F_clSubGridColor := TComponent(Sender).Tag; DrawNow; end; procedure TApp_LenZoom.actGrid_SelColorExecute(Sender: TObject); //グリッド色選択 var l_Action: TAction; lb_Shift, lb_Ctrl, lb_Disp: Boolean; begin TAction(Sender).Checked := True; if (Sender = actGrid_SelColor) then begin l_Action := actGrid_SelColor; end else if (Sender = actGrid_SelSubColor) then begin l_Action := actGrid_SelSubColor; end else begin Exit; end; lb_Shift := gfnbKeyState(VK_SHIFT); lb_Ctrl := gfnbKeyState(VK_CONTROL); lb_Disp := False; if (lb_Ctrl) then begin //画面の色をグリッド色にセット l_Action.Tag := F_rDispInfo.clColorRef; end else if (lb_Shift) then begin //画面の反転色をグリッド色にセット l_Action.Tag := gfnclColorRevers(F_rDispInfo.clColorRef); end else begin ColorDialog.Color := TColor(l_Action.Tag); if (ColorDialog.Execute) then begin l_Action.Tag := ColorDialog.Color; lb_Disp := True; end; end; if (Sender = actGrid_SelColor) then begin F_clGridColor := l_Action.Tag; end else if (Sender = actGrid_SelSubColor) then begin F_clSubGridColor := l_Action.Tag; end; //グリッドが非表示なら表示させる actGrid_Disp.Checked := actGrid_Disp.Checked or lb_Shift or lb_Ctrl or lb_Disp; FormResize(nil); end; //------------------------------------------------------------------------------ //ユーザー指定座標の原点指定 procedure TApp_LenZoom.actPos_UserPosSetExecute(Sender: TObject); {Ctrl,Shift+Ctrl} begin if (gfnbKeyState(VK_SHIFT) and gfnbKeyState(VK_CONTROL)) then begin //Shift+Ctrl+Spaceで(0, 0)にリセット F_rDispInfo.ptUserPos := Point(0, 0); end else if (gfnbKeyState(VK_CONTROL)) then begin //ユーザー指定座標の原点へカーソルを移動 MoveCursorToPoint(actPos_UserPosSet); end else begin if (actCapture_Pause.Checked) and not(gfnbKeyState(VK_SHIFT)) then begin F_rDispInfo.ptUserPos := F_rDispInfo.ptMousePos end else begin F_rDispInfo.ptUserPos := gfnptMousePosGet; if not(actPos_User.Checked) then begin actPos_User.Checked := True; FormResize(nil); end; end; end; DrawNow; end; //------------------------------------------------------------------------------ //常に手前に表示 procedure TApp_LenZoom.actOpt_StayOnTopExecute(Sender: TObject); var lh_InsertAfter: HWND; li_Flag: UINT; begin if (Sender <> nil) then begin actOpt_StayOnTop.Checked := not(actOpt_StayOnTop.Checked); end; if (actOpt_StayOnTop.Checked) then begin lh_InsertAfter := HWND_TOPMOST; end else begin lh_InsertAfter := HWND_NOTOPMOST; end; li_Flag := SWP_NOMOVE or SWP_NOSIZE or SWP_NOACTIVATE; Windows.SetWindowPos(Self.Handle, lh_InsertAfter, 0, 0, 0, 0, li_Flag); DrawNow; end; //フォントサイズ procedure TApp_LenZoom.actOpt_BigFontExecute(Sender: TObject); begin with F_bmpDraw.Canvas do begin if (actOpt_BigFont.Checked) then begin Font.Size := actOpt_BigFont.Tag; end else begin Font.Size := 9; end; F_iFontHeight := Trunc(TextHeight('A') * 1.2) +1; //ラインを引くため下に1ピクセル余裕を持たせる F_iFontWidth := TextWidth('あ') + 2; F_iInfoLeft := F_iFontHeight + TextWidth(Format(F_GetDispFmt(G_ciFMTZOOM), [F_iZoom])) + 8; //8ピクセル離す F_iVLine := TextWidth('COLORREF') + (TextWidth(' ') div 2); end; FormResize(nil); end; procedure TApp_LenZoom.actOpt_NoSelfCaptureExecute(Sender: TObject); //自分自身をキャプチャしない var ls_OSName: WideString; begin ls_OSName := gfnsOsNameGet; if not(G_bIsNtOS) or (ls_OSName = 'NT') then begin actOpt_NoSelfCapture.Checked := False; AlphaBlend := False; Exit; end; AlphaBlend := (mniOpt_NoSelfCapture.Visible and actOpt_NoSelfCapture.Checked); Sleep(100); //少し経ってからでないと最初の一度だけうまくキャプチャできない DrawNow; end; //------------------------------------------------------------------------------ //定点キャプチャ、一時停止の文字列を一定時間表示した後元に戻す procedure TApp_LenZoom.Timer_InfomationTimer(Sender: TObject); begin F_sInfomation := ''; Timer_Infomation.Enabled := False; DrawNow; end; //一時停止 procedure TApp_LenZoom.actCapture_PauseExecute(Sender: TObject); var ldc_Desktop : HDC; li_Rop : DWORD; begin if (gfnbKeyState(VK_SHIFT)) or (Sender = actCapture_UpDate) then begin //[Shift]と更新 //F_SetPoint; //キャプチャポイント現在のカーソル位置にセット。 //このプログラムでは情報をキャッシュしないので最新の情報に更新することで実現。 if (Sender <> actCapture_Update) then begin //更新の場合はキャプチャポイントを移動させない。 F_rDispInfo.ptMousePos := gfnptMousePosGet; end; actCapture_Pause.Checked := True; end else if not(gfnbKeyState(VK_CONTROL)) then begin //↑と↓の処理があるのでAutoCheckプロパティをTrueにできないので自力で反転させる。 actCapture_Pause.Checked := not(actCapture_Pause.Checked); end else begin //[Ctrl]のみ //キャプチャポイントにカーソルを移動 MoveCursorToPoint(Sender); Exit; end; Timer_Main.Enabled := not(actCapture_Pause.Checked); if (actCapture_Pause.Checked) then begin actCapture_Pause.Tag := 1; DrawNow; //↓の処理に少し時間がかかるため先に一時停止の状態表示にする。 with F_bmpDesktop do begin //マルチモニターも含めたデスクトップ全部のキャプチャ Width := MyMonitors.ScreenWidth; Height := MyMonitors.ScreenHeight; Canvas.FillRect(Rect(0, 0, Width, Height)); if (actOpt_NoSelfCapture.Checked) or (actCapture_Lupe.Checked) then begin //自身を含めない li_Rop := SRCCOPY; end else begin li_Rop := SRCCOPY or CAPTUREBLT; end; ldc_Desktop := CreateDC('DISPLAY', nil, nil, nil); try Windows.BitBlt( Canvas.Handle, 0, 0, Width, Height, ldc_Desktop, MyMonitors.ScreenLeft, MyMonitors.ScreenTop, li_Rop ); finally DeleteDC(ldc_Desktop); end; end; { if not(actOpt_NoSelfCapture.Checked) then begin AlphaBlend := False; end; } actCapture_Pause.Tag := 0; end else begin if (F_iZoomBak > 0) then begin F_iZoom := F_iZoomBak; F_iZoomBak := -1; end; end; Timer_InfomationTimer(Sender); FormResize(nil); end; procedure TApp_LenZoom.actCapture_UpdateExecute(Sender: TObject); //更新 begin if (actCapture_Pause.Checked) then begin //一時停止時のみ動作させる。 actCapture_PauseExecute(actCapture_Update); end; end; procedure TApp_LenZoom.actCapture_LupeExecute(Sender: TObject); begin if not(gfnbIsOSUpper2000) then begin //2000未満はAlphaBlendには非対応なので処理を抜ける。 actCapture_Lupe.Checked := False; Exit; end; if (actCapture_Lupe.Checked) then begin //ルーペモード //AlphaBlendをTrueにセットする必要があるので「自身をキャプチャしない」を無効にする actOpt_NoSelfCapture.Enabled := False; if not(Self.AlphaBlend) then begin Self.AlphaBlend := True; end; end else begin //無効にした「自身をキャプチャしない」を元に戻す actOpt_NoSelfCapture.Enabled := True; if not(actOpt_NoSelfCapture.Checked) then begin //自身をキャプチャする設定になっていた Self.AlphaBlend := False; end; end; DrawNow; end; //定点キャプチャ procedure TApp_LenZoom.actCapture_FixedExecute(Sender: TObject); {Shift,Ctrl} //マウスカーソルに追従せず、一点をキャプチャし続ける begin if (gfnbKeyState(VK_CONTROL)) then begin MoveCursorToPoint(Sender); Exit; end else if (gfnbKeyState(VK_SHIFT)) then begin F_SetPoint; Exit; end; actCapture_Fixed.Checked := not(actCapture_Fixed.Checked); F_rDispInfo.ptMousePos := gfnptMousePosGet; Timer_InfomationTimer(Sender); DrawNow; end; //スムースキャプチャ procedure TApp_LenZoom.actOpt_SmoothCaptureExecute(Sender: TObject); //マウスカーソルを動かしていない時でもキャプチャを間引かない const lci_SMOOTH = 30; lci_NORMAL = 60; begin if (actOpt_SmoothCapture.Checked) then begin Timer_Main.Interval := lci_SMOOTH; end else begin Timer_Main.Interval := lci_NORMAL; end; if (Sender <> nil) then begin Timer_InfomationTimer(Sender); end; DrawNow end; function TApp_LenZoom.F_GetDispFmt(iIndex: Integer): String; //表示用形式文字列を返す begin if (iIndex < 0) or (iIndex > G_ciFMTCOUNT) then begin Result := ''; end else begin Result := G_csDISPFMT[iIndex]; end; end; function TApp_LenZoom.F_GetCopyFmt(iIndex: Integer): String; //コピー用形式文字列を返す begin if (iIndex < 0) or (iIndex > G_ciFMTCOUNT) then begin Result := ''; end else begin if (gfnbKeyState(VK_SHIFT)) then begin Result := G_csCOPYFMT[iIndex, 1]; end else begin Result := G_csCOPYFMT[iIndex, 0]; end; end; end; function TApp_LenZoom.F_GetCopyZoomGrid: Boolean; //グリッドも含めコピーするか begin if (gfnbKeyState(VK_SHIFT)) then begin Result := (Copy(G_csCOPYFMT[G_ciFMTZOOM, 1], 1, 1) <> '0'); //10の位 end else begin Result := (Copy(G_csCOPYFMT[G_ciFMTZOOM, 0], 1, 1) <> '0'); //10の位 end; end; procedure TApp_LenZoom.F_ExecuteCmd(iCmd: Word); var l_Action: TAction; begin case iCmd of //[Zoom] G_ciCMDZOOM_1: l_Action := actZoom_1; G_ciCMDZOOM_2: l_Action := actZoom_2; G_ciCMDZOOM_3: l_Action := actZoom_3; G_ciCMDZOOM_4: l_Action := actZoom_4; G_ciCMDZOOM_6: l_Action := actZoom_6; G_ciCMDZOOM_8: l_Action := actZoom_8; G_ciCMDZOOM_10: l_Action := actZoom_10; G_ciCMDZOOM_12: l_Action := actZoom_12; G_ciCMDZOOM_16: l_Action := actZoom_16; G_ciCMDZOOM_20: l_Action := actZoom_20; G_ciCMDZOOM_UP: l_Action := actZoom_Up; G_ciCMDZOOM_DOWN: l_Action := actZoom_Down; //[Grid] G_ciCMDGRID_DISP: l_Action := actGrid_Disp; G_ciCMDGRID_GRAY: l_Action := actGrid_Gray; G_ciCMDGRID_INVERT: l_Action := actGrid_Invert; G_ciCMDGRID_TRANSPARENT: l_Action := actGrid_Transparent; G_ciCMDGRID_SELCOLOR: l_Action := actGrid_SelColor; G_ciCMDGRID_SUBBLUE: l_Action := actGrid_SubBlue; G_ciCMDGRID_SELSUBCOLOR: l_Action := actGrid_SelSubColor; //[Color] G_ciCMDCOLOR_RGB: l_Action := actColor_RGB; G_ciCMDCOLOR_HTML: l_Action := actColor_HTML; G_ciCMDCOLOR_COLORREF: l_Action := actColor_COLORREF; G_ciCMDCOLOR_INFOONOFF: l_Action := actColor_InfoOnOff; //[Position] G_ciCMDPOS_SCREEN: l_Action := actPos_Screen; G_ciCMDPOS_CLIENT: l_Action := actPos_Client; G_ciCMDPOS_USER: l_Action := actPos_User; G_ciCMDPOS_USERPOSSET: l_Action := actPos_UserPosSet; G_ciCMDPOS_INFOONOFF: l_Action := actPos_InfoOnOff; //[WindowInfo] G_ciCMDWININFO_HANDLE: l_Action := actWinInfo_Handle; G_ciCMDWININFO_CLASSNAME: l_Action := actWinInfo_ClassName; G_ciCMDWININFO_TEXT: l_Action := actWinInfo_Text; G_ciCMDWININFO_WINDOWSIZE: l_Action := actWinInfo_WindowSize; G_ciCMDWININFO_CLIENTSIZE: l_Action := actWinInfo_ClientSize; G_ciCMDWININFO_RECT: l_Action := actWinInfo_Rect; G_ciCMDWININFO_EXENAME: l_Action := actWinInfo_ExeName; G_ciCMDWININFO_INFOONOFF: l_Action := actWinInfo_InfoOnOff; //[Copy] G_ciCMDCOPY_PICTURE: l_Action := actCopy_Picture; G_ciCMDCOPY_COLORRGB: l_Action := actCopy_ColorRGB; G_ciCMDCOPY_COLORHTML: l_Action := actCopy_ColorHTML; G_ciCMDCOPY_COLORCOLORREF: l_Action := actCopy_ColorColorRef; G_ciCMDCOPY_POSSCREEN: l_Action := actCopy_PosScreen; G_ciCMDCOPY_POSCLIENT: l_Action := actCopy_PosClient; G_ciCMDCOPY_POSUSER: l_Action := actCopy_PosUser; G_ciCMDCOPY_WININFOHANDLE: l_Action := actCopy_WInfoHandle; G_ciCMDCOPY_WININFOCLASSNAME: l_Action := actCopy_WInfoClassName; G_ciCMDCOPY_WININFOTEXT: l_Action := actCopy_WInfoText; G_ciCMDCOPY_WININFOWINDOWSIZE: l_Action := actCopy_WInfoWindowSize; G_ciCMDCOPY_WININFOCLIENTSIZE: l_Action := actCopy_WInfoClientSize; G_ciCMDCOPY_WININFORECT: l_Action := actCopy_WInfoRect; G_ciCMDCOPY_WININFOEXENAME: l_Action := actCopy_WInfoExeName; //[Capture] G_ciCMDCAPTURE_LUPE: l_Action := actCapture_Lupe; G_ciCMDCAPTURE_FIXED: l_Action := actCapture_Fixed; G_ciCMDCAPTURE_PAUSE: l_Action := actCapture_Pause; G_ciCMDCAPTURE_UPDATE: l_Action := actCapture_Update; G_ciCMDCAPTURE_DISP_X1: l_Action := actCapture_Disp_x1; //[Option] G_ciCMDOPT_STAYONTOP: l_Action := actOpt_StayOnTop; G_ciCMDOPT_BIGFONT: l_Action := actOpt_BigFont; G_ciCMDOPT_NOSELFCAPTURE: l_Action := actOpt_NoSelfCapture; G_ciCMDOPT_SMOOTHCAPTURE: l_Action := actOpt_SmoothCapture; //[Menu] G_ciCMDMENU_MAIN: l_Action := actMenu_Main; //[Move] G_ciCMDMOVE_UP: l_Action := actMove_Up; G_ciCMDMOVE_DOWN: l_Action := actMove_Down; G_ciCMDMOVE_LEFT: l_Action := actMove_Left; G_ciCMDMOVE_RIGHT: l_Action := actMove_Right; G_ciCMDMOVE_MONITOR: l_Action := actMove_Monitor; //[File] G_ciCMDFILE_MINIMIZE: l_Action := actFile_Minimize; G_ciCMDFILE_EXIT: l_Action := actFile_Exit; //[Help] G_ciCMDHELP: l_Action := actHelp; else l_Action := nil; end; if (l_Action <> nil) then begin if (l_Action.AutoCheck) then begin l_Action.Checked := not(l_Action.Checked); end; l_Action.OnExecute(l_Action); end else begin Beep; end; end; procedure TApp_LenZoom.FormKeyDown(Sender: TObject; var Key: Word; Shift: TShiftState); //キーを押している間だけ倍率を1倍にする var i: Integer; begin if (ssAlt in Shift) then begin Exit; end; for i := 0 to High(G_rShortCutKeys) do begin if (G_rShortCutKeys[i].iKey = Key) then begin case (G_rShortCutKeys[i].iCommand) of G_ciCMDMOVE_UP, G_ciCMDMOVE_DOWN, G_ciCMDMOVE_LEFT, G_ciCMDMOVE_RIGHT: begin F_ExecuteCmd(G_rShortCutKeys[i].iCommand); Key := 0; end; G_ciCMDCAPTURE_DISP_X1: begin F_Capture_KeyDown; Key := 0; end; end; end; end; end; procedure TApp_LenZoom.FormKeyUp(Sender: TObject; var Key: Word; Shift: TShiftState); var i: Integer; begin if (ssAlt in Shift) then begin Exit; end; if (Key = VK_APPS) then begin actMenu_MainExecute(nil); Key := 0; end else begin for i := 0 to High(G_rShortCutKeys) do begin if (G_rShortCutKeys[i].iKey = Key) then begin case (G_rShortCutKeys[i].iCommand) of G_ciCMDMOVE_UP, G_ciCMDMOVE_DOWN, G_ciCMDMOVE_LEFT, G_ciCMDMOVE_RIGHT: begin //KeyDownで処理済なのでここでは何もしない Key := 0; end; G_ciCMDCAPTURE_DISP_X1: begin F_Capture_KeyUp; Key := 0; end; else begin F_ExecuteCmd(G_rShortCutKeys[i].iCommand); Key := 0; end; end; Exit; end; end; end; end; procedure TApp_LenZoom.F_Capture_KeyDown; //実寸表示にする begin if (F_iZoomBak < 0) then begin //キーを押している間だけ倍率を1倍にする F_iZoomBak := F_iZoom; F_iZoom := 1; F_iPassTime := 0; FormResize(nil); end; end; procedure TApp_LenZoom.F_Capture_KeyUp; //↑を元に戻す begin if (F_iZoomBak > 0) then begin F_iZoom := F_iZoomBak; F_iZoomBak := -1; F_iPassTime := 0; FormResize(nil); end; end; procedure TApp_LenZoom.F_Capture_MovePoint(ptPos: TPoint); const lci_Threshold = 5; lci_Wait = 40; var i, li_Start, li_Time: DWORD; begin if ((Abs(ptPos.X - F_rDispInfo.ptMousePos.X) > lci_Threshold) or (Abs(ptPos.Y - F_rDispInfo.ptMousePos.Y) > lci_Threshold)) then begin //移動をアニメーション li_Start := Windows.GetTickCount; for i := 1 to lci_Threshold -1 do begin F_rDispInfo.ptMousePos := Point( F_rDispInfo.ptMousePos.X + gfniRound(((ptPos.X - F_rDispInfo.ptMousePos.X) / lci_Threshold) * i), F_rDispInfo.ptMousePos.Y + gfniRound(((ptPos.Y - F_rDispInfo.ptMousePos.Y) / lci_Threshold) * i) ); DrawNow; li_Time := Windows.GetTickCount; if (li_Start + (i * lci_Wait) > li_Time) then begin Windows.Sleep(li_Start + (i * lci_Wait) - li_Time); end; end; end; F_rDispInfo.ptMousePos := ptPos; Timer_InfomationTimer(nil); DrawNow; end; //一時停止中にダブルクリックした点をキャプチャポジションにする procedure TApp_LenZoom.FormDblClick(Sender: TObject); var // i, li_Start, li_Time: DWORD; lpt_Pos: TPoint; lr_Monitor: TMyMonitorPos; begin if (actCapture_Fixed.Checked) then begin lpt_Pos := Point( gfniNumLimit(F_rDispInfo.ptMousePos.X + (F_ptMvClientMousePos.X) div F_iZoom - F_szDesktop.Left, 0, MyMonitors.ScreenWidth -1), gfniNumLimit(F_rDispInfo.ptMousePos.Y + (F_ptMvClientMousePos.Y) div F_iZoom - F_szDesktop.Top, 0, MyMonitors.ScreenHeight -1) ); lr_Monitor := gfnrScreenToMonitor(lpt_Pos); if ((lpt_Pos.X <> F_rDispInfo.ptMousePos.X) or ( lpt_Pos.Y <> F_rDispInfo.ptMousePos.Y)) //前回から動いていて and (lr_Monitor.MonitorNum >= 0) //モニターの範囲内 then begin F_Capture_MovePoint(lpt_Pos); end; end; end; procedure TApp_LenZoom.MoveCursorToPoint(Sender: TObject); //マウスカーソルをキャプチャポイントへ移動 const lci_Threshold = 10; lci_Wait = 10; var i, li_Start, li_Time: DWORD; lpt_Cursor, lpt_Point: TPoint; begin //定点キャプチャ・一時停止時 if (Sender = actPos_UserPosSet) then begin //ユーザー指定の原点 lpt_Point := F_rDispInfo.ptUserPos; end else if (actCapture_Fixed.Checked) or (actCapture_Pause.Checked) then begin //一時停止か定点キャプチャ時 lpt_Point := F_rDispInfo.ptMousePos; end else begin //それ以外の場合はあまり意味がないので処理を抜ける Exit; end; lpt_Cursor := gfnptMousePosGet; if (Abs(lpt_Cursor.X - lpt_Point.X) > lci_Threshold) or (Abs(lpt_Cursor.Y - lpt_Point.Y) > lci_Threshold) then begin //カーソルを瞬時に移動させるのではなく残像を見せつつ移動させる li_Start := Windows.GetTickCount; for i := 1 to lci_Threshold -1 do begin Windows.SetCursorPos( lpt_Cursor.X - gfniRound(((lpt_Cursor.X - lpt_Point.X) / lci_Threshold) * i), lpt_Cursor.Y - gfniRound(((lpt_Cursor.Y - lpt_Point.Y) / lci_Threshold) * i) ); li_Time := Windows.GetTickCount; if (li_Start + (i * lci_Wait) > li_Time) then begin Windows.Sleep(li_Start + (i * lci_Wait) - li_Time); end; end; end; Windows.SetCursorPos(lpt_Point.X, lpt_Point.Y); end; procedure TApp_LenZoom.F_SetPoint; //現在のマウスカーソルの位置をキャプチャポイントに設定 begin //定点キャプチャ・一時停止時 if (actCapture_Fixed.Checked) or (actCapture_Pause.Checked) then begin F_Capture_MovePoint(gfnptMousePosGet); end; end; //------------------------------------------------------------------------------ //最小化 procedure TApp_LenZoom.actFile_MinimizeExecute(Sender: TObject); begin Application.Minimize; end; //終了 procedure TApp_LenZoom.actFile_ExitExecute(Sender: TObject); begin Close; end; //============================================================================== procedure TApp_LenZoom.F_PushInfomation(sText: WideString); //1行情報表示へ情報をプッシュ begin F_sInfomation := sText; Timer_Infomation.Enabled := True; DrawNow; end; //ptPosの点上にある可視ウィンドウを返す。 type T_TopWindow = record hTop, hParent: HWND; end; P_TopWindow = ^T_TopWindow; function lfnb_EnumChildProc(hHandle: HWND; pTopWindow: Pointer): BOOL; stdcall; var lh_Parent: HWND; begin Result := True; with App_LenZoom do begin if (IsWindowVisible(hHandle)) and (PtInRect(gfnrcWindowRectGet(hHandle), F_rDispInfo.ptMousePos)) then begin lh_Parent := gfnhParentWindowGet(hHandle); if (lh_Parent = T_TopWindow(pTopWindow^).hTop) then begin //直前に列挙された対象ウィンドウの子ウィンドウだった //hTopとhParentを書き換える //子ウィンドウがあるかもしれないので処理を続ける T_TopWindow(pTopWindow^).hTop := hHandle; T_TopWindow(pTopWindow^).hParent := lh_Parent; end else begin //親ウィンドウが同じなら兄弟ウィンドウ。 //しかし列挙されるのは手前のウィンドウからなのでその場合はhTopは書き換ず処理を抜ける。 //親ウィンドウが直前のウィンドウでもない //おじさんおばさんウィンドウ、あるいはさらに遡ってのウィンドウであるのでこれまたhTopを書き換えず処理を抜ける Result := False; end; end; end; end; function lfnb_EnumWindowsProc(hHandle: HWND; pTopWindow: Pointer):BOOL; stdcall; //トップレベルウィンドウを列挙する var lrg_Region: HRGN; lpt_Pos: TPoint; lrc_Rect, lrc_Client: TRect; begin with App_LenZoom do begin lrc_Rect := gfnrcWindowRectGet(hHandle); if (IsWindowVisible(hHandle)) //可視ウィンドウのみ and (PtInRect(lrc_Rect, F_rDispInfo.ptMousePos)) //ウィンドウのRect内にマウスカーソルがある then begin if (actOpt_NoSelfCapture.Checked) and (actOpt_NoSelfCapture.Enabled) and ((GetWindowLong(hHandle, GWL_EXSTYLE) and WS_EX_LAYERED) = WS_EX_LAYERED) then begin //自身をキャプチャしない設定で対象ウィンドウがレイヤードである場合キャプチャできていないので次のウィンドウに処理を移す Result := True; end else if (actCapture_Lupe.Checked and actCapture_Lupe.Enabled) and (hHandle = App_LenZoom.Handle) then begin //ルーペモード。 Result := True; end else begin Result := False; lrg_Region := CreateRectRgn(0, 0, 0, 0); try if (GetWindowRgn(hHandle, lrg_Region) <> ERROR) then begin lpt_Pos.X := F_rDispInfo.ptMousePos.X - lrc_Rect.Left; lpt_Pos.Y := F_rDispInfo.ptMousePos.Y - lrc_Rect.Top; if (PtInRegion(lrg_Region, lpt_Pos.X, lpt_Pos.Y)) then begin //リージョン内だったので処理を抜ける end else begin //リージョン外だったので処理を続ける Result := True; end; end; finally DeleteObject(lrg_Region); end; if (Result = False) then begin T_TopWindow(pTopWindow^).hTop := hHandle; T_TopWindow(pTopWindow^).hParent := gfnhParentWindowGet(hHandle); lrc_Client := gfnrcClientRectGet(hHandle); if (lrc_Client.Right > 0) or (lrc_Client.Bottom > 0) then begin EnumChildWindows(hHandle, @lfnb_EnumChildProc, LPARAM(pTopWindow)); end; end; end; end else begin Result := True; end; end; end; function TApp_LenZoom.F_GetWindow(ptPos: TPoint): HWND; var lr_TopWindow: T_TopWindow; lh_Handle: HWND; begin if( (mniOpt_NoSelfCapture.Visible) and (actOpt_NoSelfCapture.Checked) and (actOpt_NoSelfCapture.Enabled) ) or (actCapture_Lupe.Checked and actCapture_Lupe.Enabled) then begin //自身をキャプチャしない FillChar(lr_TopWindow, SizeOf(lr_TopWindow), 0); EnumWindows(@lfnb_EnumWindowsProc, LPARAM(@lr_TopWindow)); Result := lr_TopWindow.hTop; end else begin lh_Handle := WindowFromPoint(ptPos); if (lh_Handle = ChildWindowFromPoint(lh_Handle, gfnptScreenToClient(lh_Handle, ptPos))) then begin Result := lh_Handle; end else begin //レイヤードウィンドウで下のウィンドウが透過するウィンドウは正しく処理できない //XPスタイルの角の丸いタイトルバーはOK FillChar(lr_TopWindow, SizeOf(lr_TopWindow), 0); EnumWindows(@lfnb_EnumWindowsProc, LPARAM(@lr_TopWindow)); Result := lr_TopWindow.hTop; end; end; end; procedure TApp_LenZoom.Timer_MainTimer(Sender: TObject); const //情報表示欄に引くラインのマージン。どれだけ文字から離すか lci_LINEMARGIN = 2; lci_MARGINLEFT = 2; const //ステータス表示の位置(順序) lci_INFO_STAYONTOP = 0; lci_INFO_SMOOTH = 1; lci_INFO_PAUSE = 2; lci_INFO_LUPE = 3; lci_INFO_FIX = 4; const lci_SUBGRID = 5; //サブグリッドの間隔 lci_SUBELSEGRID = 2; //サブグリッドを違う色で引く間隔 lci_GRIDMARGIN = 1; //倍率が低いときのグリッドとカーソルポイントとの間隔 var lpt_Pos: TPoint; li_TickCount: DWORD; ldc_Desktop: HDC; lcl_BackColor: TColor; lrc_Rect: TRect; i, li_Width, li_Height, li_BoxLen, li_ShiftLine: Integer; li_Rop: DWORD; begin Application.ProcessMessages; if (F_bThroughTimer) then begin Exit; end; F_bThroughTimer := True; if (actCapture_Lupe.Checked and actCapture_Lupe.Enabled) then begin //F_szZoomは拡大画像の大きさであって拡大画面の大きさではないことに注意。 //拡大画像は拡大率によって若干ながらも大きさが変動するので拡大画面の中心を得たい今回のような用途には使えない。 //サイズ計算の時にグリッドをよけるために+1しているので-1が必要。 lpt_Pos.X := -1 + Self.ClientOrigin.X + gfniRound(ClientWidth / 2); lpt_Pos.Y := -1 + Self.ClientOrigin.Y + gfniRound((ClientHeight - gfniRectHeight(F_rcInfo)) / 2); end else if ((actCapture_Fixed.Checked) or (actCapture_Pause.Checked)) then begin lpt_Pos := F_rDispInfo.ptMousePos; //固定キャプチャ end else begin Windows.GetCursorPos(lpt_Pos); end; li_TickCount := Windows.GetTickCount; if (lpt_Pos.X <> F_rDispInfo.ptMousePos.X) or (lpt_Pos.Y <> F_rDispInfo.ptMousePos.Y) //前回表示の時と今回とマウスカーソルの位置が違っている or (F_iPassTime = 0) //経過時間が0である or (Abs(li_TickCount - F_iPassTime) > Timer_Main.Tag) //前回描画時からリフレッシュ時間を過ぎている。 or (actOpt_SmoothCapture.Checked) //スムーズキャプチャ(間引き無し) then begin //上記のどれかに合致したらば↓の処理に入る with F_rDispInfo, F_bmpDraw.Canvas do begin ptMousePos := lpt_Pos; Brush.Color := clBlack; FillRect(Rect(0, 0, ClientWidth, F_rcInfo.Top)); if (Timer_Main.Enabled = False) and (actCapture_Pause.Tag = 0) //actCapture_Pause.Tagが1の時はキャッシュを使わない then begin //一時停止とズーム画像コピーのとき Windows.StretchBlt( Handle, 0, 0, F_szZoom.Width, F_szZoom.Height, F_bmpDesktop.Canvas.Handle, ptMousePos.X - F_szDesktop.Left + (-MyMonitors.ScreenLeft), ptMousePos.Y - F_szDesktop.Top + (-MyMonitors.ScreenTop), F_szDesktop.Width, F_szDesktop.Height, SRCCOPY ); end else begin //リアルタイムのデスクトップをキャプチャ ldc_Desktop := CreateDC('DISPLAY', nil, nil, nil); try if ((actOpt_NoSelfCapture.Checked) and (actOpt_NoSelfCapture.Enabled)) or ((actCapture_Lupe.Checked) and (actCapture_Lupe.Enabled)) then begin li_Rop := SRCCOPY; end else begin li_Rop := SRCCOPY or CAPTUREBLT; end; //レイヤードウィンドウはStretchBltでは拡大コピーできないようなので一度等倍でコピーしてから拡大する F_bmpDesktop.Canvas.Brush.Color := clBlack; F_bmpDesktop.Canvas.FillRect(Rect(0, 0, F_szDesktop.Width, F_szDesktop.Height)); BitBlt(F_bmpDesktop.Canvas.Handle, 0, 0, F_szDesktop.Width, F_szDesktop.Height, ldc_Desktop, ptMousePos.X - F_szDesktop.Left, ptMousePos.Y - F_szDesktop.Top, li_Rop); StretchBlt(Handle, 0, 0, F_szZoom.Width, F_szZoom.Height, F_bmpDesktop.Canvas.Handle, 0, 0, F_szDesktop.Width, F_szDesktop.Height, SRCCOPY); finally DeleteDC(ldc_Desktop); end; end; //グリッド描画 if (actGrid_Disp.Checked) then begin if (F_iZoom >= FciMINGRID) then begin //ペンをセット Pen.Color := F_clGridColor; Pen.Mode := F_pmPenMode; //縦線を引く for i := 1 to F_iHGrid do begin li_Width := i * F_iZoom; MoveTo(li_Width, 0); LineTo(li_Width, F_rcInfo.Top); end; //横線を引く for i := 1 to F_iVGrid do begin li_Height := i * F_iZoom; MoveTo(0, li_Height); LineTo(ClientWidth, li_Height); end; //サブグリッドを引く Pen.Color := F_clSubGridColor; Pen.Mode := pmCopy; //縦線を引く //キャプチャポイントを中心にしてサブグリッドを引くため li_ShiftLine := ((gfniRound(F_iHGrid / 2) -1) mod lci_SUBGRID) * F_iZoom; for i := 0 to F_iHGrid div lci_SUBGRID do begin li_Width := li_ShiftLine + (i * F_iZoom * lci_SUBGRID); MoveTo(li_Width, 0); LineTo(li_Width, F_rcInfo.Top); end; //横線を引く //キャプチャポイントを中心にしてサブグリッドを引くため li_ShiftLine := ((gfniRound(F_iVGrid / 2) -1) mod lci_SUBGRID) * F_iZoom; for i := 0 to F_iVGrid div lci_SUBGRID do begin li_Height := li_ShiftLine + (i * F_iZoom * lci_SUBGRID); MoveTo(0, li_Height); LineTo(ClientWidth, li_Height); end; end else begin //倍率が低くてグリッドを引けないのでキャプチャポイントのグリッドだけ引く //中心線を引く //サブグリッドあり Pen.Color := F_clSubGridColor; Pen.Mode := pmCopy; //縦線を引く MoveTo(F_ptColorPos.X, 0); LineTo(F_ptColorPos.X, F_ptColorPos.Y - F_GetPointShift - lci_GRIDMARGIN); MoveTo(F_ptColorPos.X, F_ptColorPos.Y + F_iZoom + F_GetPointShift + lci_GRIDMARGIN); LineTo(F_ptColorPos.X, F_rcInfo.Top); //横線を引く MoveTo(0, F_ptColorPos.Y); LineTo(F_ptColorPos.X - F_GetPointShift - lci_GRIDMARGIN, F_ptColorPos.Y); MoveTo(F_ptColorPos.X + F_iZoom + F_GetPointShift + lci_GRIDMARGIN, F_ptColorPos.Y); LineTo(ClientWidth, F_ptColorPos.Y); end; end; //現在のマウスカーソルのポイント表示 li_BoxLen := F_iZoom + F_GetPointShift; Pen.Mode := pmNot; li_Width := F_ptColorPos.X - F_GetPointShift; li_Height := F_ptColorPos.Y - F_GetPointShift; PolyLine([ Point(li_Width , li_Height), Point(li_Width + li_BoxLen, li_Height), //→ Point(li_Width + li_BoxLen, li_Height + li_BoxLen), //↓ Point(li_Width , li_Height + li_BoxLen), //← Point(li_Width , li_Height) //↑ ]); Pen.Mode := pmCopy; //情報表示---------------------------------------------------------------------- //カラー値は表示させていなくてもコピーで使うことがあるのでここに置く clColorRef := Pixels[F_ptColorPos.X, F_ptColorPos.Y]; iRed := clColorRef and $0000FF; iGreen := clColorRef and $00FF00 div $000100; iBlue := clColorRef and $FF0000 div $010000; clColor := (iRed * $010000) + (iGreen * $000100) + iBlue; //マウスポジションの座標変換 if (actCapture_Pause.Checked) and (actCapture_Pause.Tag = 0) //一時停止の始めに時間のかかる処理を行うので、その場合はこの中に入らない then begin //一時停止中 end else begin //表示させていないものでも一時停止時に表示させることができるのでこの位置でセット ptClientPos := ptMousePos; hWinHandle := F_GetWindow(ptMousePos); Windows.ScreenToClient(hWinHandle, ptClientPos); ptClientPos := Point(ptMousePos.X - ptClientPos.X, ptMousePos.Y - ptClientPos.Y); sWinClass := gfnsClassNameGet(hWinHandle); sWinText := gfnsWindowTextGet(hWinHandle); Windows.GetWindowRect(hWinHandle, lrc_Rect); rcWinRect := lrc_Rect; lpt_Pos := lrc_Rect.TopLeft; Windows.ScreenToClient(gfnhParentWindowGet(hWinHandle), lpt_Pos); with szWindowSize do begin Left := lpt_Pos.X; Top := lpt_Pos.Y; Width := lrc_Rect.Right - lrc_Rect.Left; Height := lrc_Rect.Bottom - lrc_Rect.Top; end; Windows.GetClientRect(hWinHandle, lrc_Rect); with szClientSize do begin Width := lrc_Rect.Right; Height := lrc_Rect.Bottom; end; sExeName := gfnsExeNameGet(hWinHandle); end; //以下は各種情報表示 ----------------------------------------------------- //情報表示枠の塗りつぶし if (GetActiveWindow <> Self.Handle) then begin //フォームがアクティブでなければ灰色表示 Brush.Color := clBtnFace; Font.Color := clBtnText; Pen.Color := clBtnShadow; end else if (actCapture_Pause.Checked) then begin //一時停止時はヒントのカラー(薄黄色) Brush.Color := clInfoBk; Font.Color := clInfoText; Pen.Color := clBtnFace; end else begin Brush.Color := clWindow; Font.Color := clWindowText; Pen.Color := clBtnFace; end; FillRect(F_rcInfo); //1行表示(倍率などの表示) li_Height := F_rcInfo.Top + lci_LINEMARGIN; if (F_sInfomation <> '') then begin //1行情報表示 if (G_bIsNtOs) then begin TextOutW(Handle, F_iFontHeight + lci_MARGINLEFT, li_Height, PWideChar(F_sInfomation), Length(F_sInfomation)); //現在のピクセルの色表示を避けるためF_iFontHeightをプラス。 end else begin TextOut(F_iFontHeight + lci_MARGINLEFT, li_Height, F_sInfomation); //現在のピクセルの色表示を避けるためF_iFontHeightをプラス。 end; end else begin { TextOut(F_iFontHeight + lci_MARGINLEFT, li_Height, Format(F_GetDispFmt(G_ciFMTZOOM), [F_iZoom])); if (actOpt_StayOnTop.Checked) then TextOut(F_iInfoLeft + F_iFontWidth * lci_INFO_STAYONTOP, li_Height -1, '↑'); //StayOnTop if (actCapture_Pause.Checked) then TextOut(F_iInfoLeft + F_iFontWidth * lci_INFO_PAUSE, li_Height -1, '停'); //Pause if (actOpt_SmoothCapture.Checked) then TextOut(F_iInfoLeft + F_iFontWidth * lci_INFO_SMOOTH, li_Height -1, '滑'); //Smooth if (actCapture_Lupe.Checked) then begin TextOut(F_iInfoLeft + F_iFontWidth * lci_INFO_FIX, li_Height, 'ル'); end else if (actCapture_Fixed.Checked) then begin TextOut(F_iInfoLeft + F_iFontWidth * lci_INFO_FIX, li_Height, Format('定' + lcsMARK_Fixed, [F_rDispInfo.ptMousePos.X, F_rDispInfo.ptMousePos.Y])); end; } TextOut(F_iFontHeight + lci_MARGINLEFT, li_Height, Format(F_GetDispFmt(G_ciFMTZOOM), [F_iZoom])); if (actOpt_StayOnTop.Checked) then ImageList_Icon.Draw(F_bmpDraw.Canvas, F_iInfoLeft + ImageList_Icon.Width * lci_INFO_STAYONTOP, li_Height -1, lci_INFO_STAYONTOP); //StayOnTop if (actCapture_Pause.Checked) then ImageList_Icon.Draw(F_bmpDraw.Canvas, F_iInfoLeft + ImageList_Icon.Width * lci_INFO_PAUSE, li_Height -1, lci_INFO_PAUSE); //Pause if (actOpt_SmoothCapture.Checked) then ImageList_Icon.Draw(F_bmpDraw.Canvas, F_iInfoLeft + ImageList_Icon.Width * lci_INFO_SMOOTH, li_Height -1, lci_INFO_SMOOTH); //Smooth if (actCapture_Lupe.Checked) then ImageList_Icon.Draw(F_bmpDraw.Canvas, F_iInfoLeft + ImageList_Icon.Width * lci_INFO_FIX, li_Height -1, lci_INFO_LUPE); //Fixと同じ場所に表示 if (actCapture_Fixed.Checked) then begin ImageList_Icon.Draw(F_bmpDraw.Canvas, F_iInfoLeft + ImageList_Icon.Width * lci_INFO_FIX, li_Height -1, lci_INFO_FIX); //Fix TextOut(F_iInfoLeft + ImageList_Icon.Width * ImageList_Icon.Count, li_Height, Format(lcsMARK_Fixed, [F_rDispInfo.ptMousePos.X, F_rDispInfo.ptMousePos.Y])); end; end; //現在のカーソル位置の色をボックスに表示 lcl_BackColor := Brush.Color; Brush.Color := clColorRef; FillRect(Rect(F_rcInfo.Left +2, F_rcInfo.Top +2 +1{ズーム画像との境界のライン分で+1}, F_iFontHeight -2, F_rcInfo.Top + F_iFontHeight -2)); //枠いっぱいではなく2ピクセルづつ狭くする Brush.Color := lcl_BackColor; //枠を描画 // Pen.Color := clBtnShadow; MoveTo(F_rcInfo.Left +1, F_rcInfo.Top +1 +1); LineTo(F_iFontHeight -2, F_rcInfo.Top +1 +1); LineTo(F_iFontHeight -2, F_rcInfo.Top + F_iFontHeight -1 -1); LineTo(F_rcInfo.Left +1, F_rcInfo.Top + F_iFontHeight -1 -1); LineTo(F_rcInfo.Left +1, F_rcInfo.Top +1 +1); //情報表示 F_PutInfo(Sender, li_Height); //縦線 MoveTo(F_iVLine, F_rcInfo.Top + F_iFontHeight +1); LineTo(F_iVLine, ClientHeight); //画像領域と情報領域の間に線を引く if (GetActiveWindow = Self.Handle) then begin Pen.Color := clActiveCaption; end else begin Pen.Color := clInActiveCaption; end; MoveTo(0, F_rcInfo.Top); LineTo(ClientWidth, F_rcInfo.Top); end; FormPaint(nil); //拡大画像と各種情報をフォームへ描画 F_iPassTime := li_TickCount; if (Timer_Main.Tag <> FciCapture_RefleshTime) then begin Timer_Main.Tag := FciCapture_RefleshTime; end; end; // if not(actCapture_Pause.Checked) then Timer_Main.Enabled := True; // Timer_Main.Enabled := lb_TimerEnabled; F_bThroughTimer := False; end; procedure TApp_LenZoom.F_PutInfo(Sender: TObject; var iInfoTop: Integer); //FormResizeとコピーとメインタイマーから呼び出されるルーチン procedure lpc_CopyToClipboard(AAction: TAction; sStr: WideString); //コピールーチン var ls_File : WideString; li_ErrMode : UINT; begin //クリップボードへコピー gpcStrToClipboard(sStr); if (AAction <> nil) then begin //AIU if (G_bIsNtOs) then begin F_PushInfomation(WideFormat(lcsFMT_COPY, [AAction.Caption, sStr])); end else begin F_PushInfomation(Format(lcsFMT_COPY, [AAction.Caption, sStr])); end; end; //Ctrlキーが押されていたらエディターを起動 if (gfnbKeyState(VK_CONTROL)) then begin //ファイルへ保存 // ls_File := gfnsFileExtChange(gfnsExeNameGet, '.txt'); ls_File := gfnsWorkFileNameGet('.txt'); li_ErrMode := SetErrorMode(SEM_FAILCRITICALERRORS); try gpcFileWriteText(ls_File, gfnsWideToAnsi(sStr)); except on EErr: Exception do begin gpcShowMessage(Format('%s'#13#13'コピー情報を書き込めませんでした', [EErr.Message]), 'エラー'); end; end; SetErrorMode(li_ErrMode); if (gfnbFileExists(ls_File)) then gpcExecute(ls_File); end; end; procedure lpc_DrawInfo(Sender: TObject; sInfo: WideString; var iTop: Integer); //メインタイマーで使われる情報表示ルーチン const //情報表示欄に引くラインのマージン。どれだけ文字から離すか lci_LINEMARGIN = 2; lci_MARGINLEFT = 2; begin if (Sender = Timer_Main) then begin F_bmpDraw.Canvas.MoveTo(0, iTop - lci_LINEMARGIN); F_bmpDraw.Canvas.LineTo(ClientWidth, iTop - lci_LINEMARGIN); if (G_bIsNtOs) then begin //NT系OSならUnicodeに対応 TextOutW(F_bmpDraw.Canvas.Handle, lci_MARGINLEFT, iTop, PWideChar(sInfo), Length(sInfo)); end else begin F_bmpDraw.Canvas.TextOut(lci_MARGINLEFT, iTop, sInfo); end; end; Inc(iTop, F_iFontHeight); end; begin Inc(iInfoTop, F_iFontHeight); with F_rDispInfo do begin //カラー値 //RGB if (Sender = actCopy_ColorRGB) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTCOLOR_RGB], [iRed, iGreen, iBlue])); end else if (actColor_RGB.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTCOLOR_RGB), [iRed, iGreen, iBlue]), iInfoTop); end; //HTML if (Sender = actCopy_ColorHtml) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTCOLOR_HTML], [clColor])); end else if (actColor_HTML.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTCOLOR_HTML), [LowerCase(IntToHex(clColor, 6))]), iInfoTop); end; //COLORREF if (Sender = actCopy_ColorCOLORRef) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTCOLOR_COLORREF], [clColorRef])); end else if (actColor_COLORREF.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTCOLOR_COLORREF), [clColorRef, LowerCase(IntToHex(clColorRef, 6))]), iInfoTop); end; //カーソル位置 //スクリーン座標 if (Sender = actCopy_PosScreen) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTPOS_SCREEN], [ptMousePos.X, ptMousePos.Y])); end else if (actPos_Screen.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTPOS_SCREEN), [ptMousePos.X, ptMousePos.Y]), iInfoTop); end; //クライアント座標 if (Sender = actCopy_PosClient) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTPOS_CLIENT], [ptMousePos.X - ptClientPos.X, ptMousePos.Y - ptClientPos.Y])); end else if (actPos_Client.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTPOS_CLIENT), [ptMousePos.X - ptClientPos.X, ptMousePos.Y - ptClientPos.Y, ptClientPos.X, ptClientPos.Y]), iInfoTop); end; //ユーザー指定座標 if (Sender = actCopy_PosUser) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTPOS_USER], [ptMousePos.X - ptUserPos.X, ptMousePos.Y - ptUserPos.Y, ptUserPos.X, ptUserPos.Y])); end; if (actPos_User.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTPOS_USER), [ptMousePos.X - ptUserPos.X, ptMousePos.Y - ptUserPos.Y, ptUserPos.X, ptUserPos.Y]), iInfoTop); end; //ウィンドウ情報 //ウィンドウハンドル if (Sender = actCopy_WInfoHandle) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTWININFO_HANDLE], [hWinHandle])); end else if (actWinInfo_Handle.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTWININFO_HANDLE), [LowerCase(IntToHex(hWinHandle, 8)), hWinHandle]), iInfoTop); end; //クラス名 if (Sender = actCopy_WInfoClassName) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTWININFO_CLASSNAME], [sWinClass])); end; if (actWinInfo_ClassName.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTWININFO_CLASSNAME), [sWinClass]), iInfoTop); end; //ウィンドウテキスト if (Sender = actCopy_WInfoText) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTWININFO_TEXT], [sWinText])); end else if (actWinInfo_Text.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTWININFO_TEXT), [sWinText]), iInfoTop); end; //ウィンドウサイズ 幅、高さ、Left値、Top値 if (Sender = actCopy_WInfoWindowSize) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTWININFO_WINDOWSIZE], [szWindowSize.Left, szWindowSize.Top, szWindowSize.Width, szWindowSize.Height, '', ''])); end else if (actWinInfo_WindowSize.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTWININFO_WINDOWSIZE), [szWindowSize.Width, szWindowSize.Height, szWindowSize.Left, szWindowSize.Top]), iInfoTop); end; //クライアントサイズ if (Sender = actCopy_WInfoClientSize) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTWININFO_CLIENTSIZE], [szClientSize.Width, szClientSize.Height])); end else if (actWinInfo_ClientSize.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTWININFO_CLIENTSIZE), [szClientSize.Width, szClientSize.Height]), iInfoTop); end; //RECT if (Sender = actCopy_WInfoRect) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTWININFO_RECT], [rcWinRect.Left, rcWinRect.Top, rcWinRect.Right, rcWinRect.Bottom])); end else if (actWinInfo_Rect.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTWININFO_RECT), [rcWinRect.Left, rcWinRect.Top, rcWinRect.Right, rcWinRect.Bottom]), iInfoTop); end; //実行ファイル名 if (Sender = actCopy_WInfoExeName) then begin lpc_CopyToClipboard(TAction(Sender), WideFormat(CopyFmt[G_ciFMTWININFO_EXENAME], [sExeName, gfnsFileNameGet(sExeName)])); end else if (actWinInfo_ExeName.Checked) then begin lpc_DrawInfo(Sender, WideFormat(F_GetDispFmt(G_ciFMTWININFO_EXENAME), [sExeName]), iInfoTop); end; end; end; function TApp_LenZoom.F_GetDrawFont: TFont; begin Result := F_bmpDraw.Canvas.Font; end; //============================================================================== procedure TApp_LenZoom.ApplicationEvents1Activate(Sender: TObject); begin DrawNow; end; procedure TApp_LenZoom.ApplicationEvents1Deactivate(Sender: TObject); begin F_Capture_KeyUp; DrawNow; end; //コピー ----------------------------------------------------------------------- procedure TApp_LenZoom.actCopy_PictureExecute(Sender: TObject); //クリップボードへ画像をコピー var ldc_Desktop: HDC; l_Bitmap: TMyBitmap; ls_File: WideString; ls_Caption: String; lb_Timer: Boolean; li_ErrMode: UINT; li_Rop: DWORD; begin l_Bitmap := TMyBitmap.Create; try l_Bitmap.Width := Self.ClientWidth; l_Bitmap.Height := Self.ClientHeight; if (F_GetCopyZoomGrid) then begin //グリッドつきでコピー Windows.BitBlt(l_Bitmap.Canvas.Handle, 0, 0, l_Bitmap.Width, l_Bitmap.Height, F_bmpDraw.Canvas.Handle, 0, 0, SRCCOPY); end else begin //グリッドなしでコピー if (actCapture_Pause.Checked) then begin Windows.StretchBlt(l_Bitmap.Canvas.Handle, 0, 0, F_szZoom.Width, F_szZoom.Height, F_bmpDesktop.Canvas.Handle, F_rDispInfo.ptMousePos.X - F_szDesktop.Left, F_rDispInfo.ptMousePos.Y - F_szDesktop.Top, F_szDesktop.Width, F_szDesktop.Height, SRCCOPY); end else begin //バッファの画像にはグリッドを引いてあるので新規にキャプチャする //一時停止ではないのでタイマーを止めておく lb_Timer := Timer_Main.Enabled; Timer_Main.Enabled := False; //無駄にはなるがF_bmpDesktopをバッファとして利用 if (actOpt_NoSelfCapture.Checked) then begin li_Rop := SRCCOPY; end else begin li_Rop := SRCCOPY or CAPTUREBLT; end; //マルチモニターも含めたデスクトップ全部のキャプチャ F_bmpDesktop.Width := MyMonitors.ScreenWidth; F_bmpDesktop.Height := MyMonitors.ScreenHeight; F_bmpDesktop.Canvas.FillRect(Rect(0, 0, F_bmpDesktop.Width, F_bmpDesktop.Height)); ldc_Desktop := CreateDC('DISPLAY', nil, nil, nil); try Windows.BitBlt(F_bmpDesktop.Canvas.Handle, 0, 0, F_bmpDesktop.Width, F_bmpDesktop.Height, ldc_Desktop, 0, 0, li_Rop); finally DeleteDC(ldc_Desktop); end; Windows.StretchBlt(l_Bitmap.Canvas.Handle, 0, 0, F_szZoom.Width, F_szZoom.Height, F_bmpDesktop.Canvas.Handle, F_rDispInfo.ptMousePos.X - F_szDesktop.Left, F_rDispInfo.ptMousePos.Y - F_szDesktop.Top, F_szDesktop.Width, F_szDesktop.Height, SRCCOPY); //情報欄もコピー DrawNow; //情報欄を更新 Windows.BitBlt(l_Bitmap.Canvas.Handle, 0, F_rcInfo.Top, l_Bitmap.Width, l_Bitmap.Height - F_rcInfo.Top, F_bmpDraw.Canvas.Handle, 0, F_rcInfo.Top, SRCCOPY); Timer_Main.Enabled := lb_Timer; end; end; ls_Caption := lcsMARK_PICTURE; Clipboard.Assign(l_Bitmap); if (gfnbKeyState(VK_CONTROL)) then begin //画像をファイルへ保存 // ls_File := gfnsFileExtChange(gfnsExeNameGet, '.bmp'); ls_File := gfnsWorkFileNameGet('.bmp'); li_ErrMode := SetErrorMode(SEM_FAILCRITICALERRORS); try l_Bitmap.SaveToFile(ls_File); except on EErr: Exception do begin Application.MessageBox(PChar(Format('%s'#13#13'コピー画像を書き込めませんでした', [EErr.Message])), 'エラー'); end; end; SetErrorMode(li_ErrMode); if (gfnbFileExists(ls_File)) then gpcExecute(ls_File); end; finally l_Bitmap.Free; end; F_PushInfomation(Format(lcsFMT_COPY, [ls_Caption, ''])); end; procedure TApp_LenZoom.actCopy_TextExecute(Sender: TObject); var li_Dummy: Integer; begin li_Dummy := 0; F_PutInfo(Sender, li_Dummy); end; procedure TApp_LenZoom.F_MouseResize(X, Y: Integer; bSizing: Boolean); const lci_MARGIN = 4; var li_SizeX, li_SizeY: Integer; begin if (bSizing) then begin ReleaseCapture; end; li_SizeX := GetSystemMetrics(SM_CXFRAME); li_SizeY := GetSystemMetrics(SM_CYFRAME); if ((X < li_SizeX * lci_MARGIN) and (Y < li_SizeY * lci_MARGIN)) then begin //左上 // SetCursor(LoadCursor(0, IDC_SIZENWSE)); Self.Cursor := crSizeNWSE; if (bSizing) then SendMessage(Self.Handle, WM_SYSCOMMAND, WPARAM(SC_SIZE or WMSZ_TOPLEFT), 0); end else if ((ClientWidth - X <= li_SizeX * lci_MARGIN) and (ClientHeight - Y <= li_SizeY * lci_MARGIN)) then begin //右下 // SetCursor(LoadCursor(0, IDC_SIZENWSE)); Self.Cursor := crSizeNWSE; if (bSizing) then SendMessage(Self.Handle, WM_SYSCOMMAND, WPARAM(SC_SIZE or WMSZ_BOTTOMRIGHT), 0); end else if ((ClientWidth - X <= li_SizeX * lci_MARGIN) and (Y < li_SizeY * lci_MARGIN)) then begin //右上 // SetCursor(LoadCursor(0, IDC_SIZENESW)); Self.Cursor := crSizeNESW; if (bSizing) then SendMessage(Self.Handle, WM_SYSCOMMAND, WPARAM(SC_SIZE or WMSZ_TOPRIGHT), 0); end else if ((X < li_SizeX * lci_MARGIN) and (ClientHeight - Y <= li_SizeY * lci_MARGIN)) then begin //左下 // SetCursor(LoadCursor(0, IDC_SIZENESW)); Self.Cursor := crSizeNESW; if (bSizing) then SendMessage(Self.Handle, WM_SYSCOMMAND, WPARAM(SC_SIZE or WMSZ_BOTTOMLEFT), 0); end else if (X < li_SizeX) then begin //左 // SetCursor(LoadCursor(0, IDC_SIZEWE)); Self.Cursor := crSizeWE; if (bSizing) then SendMessage(Self.Handle, WM_SYSCOMMAND, WPARAM(SC_SIZE or WMSZ_LEFT), 0); end else if (ClientWidth - X <= li_SizeX) then begin //右 // SetCursor(LoadCursor(0, IDC_SIZEWE)); Self.Cursor := crSizeWE; if (bSizing) then SendMessage(Self.Handle, WM_SYSCOMMAND, WPARAM(SC_SIZE or WMSZ_RIGHT), 0); end else if (Y < li_SizeY) then begin //上 // SetCursor(LoadCursor(0, IDC_SIZENS)); Self.Cursor := crSizeNS; if (bSizing) then SendMessage(Self.Handle, WM_SYSCOMMAND, WPARAM(SC_SIZE or WMSZ_TOP), 0); end else if (ClientHeight - Y <= li_SizeY) then begin //下 // SetCursor(LoadCursor(0, IDC_SIZENS)); Self.Cursor := crSizeNS; if (bSizing) then SendMessage(Self.Handle, WM_SYSCOMMAND, WPARAM(SC_SIZE or WMSZ_BOTTOM), 0); end else begin //つかんで移動 //最大化しても移動できてしまったのでそれへの対処 // SetCursor(LoadCursor(0, IDC_ARROW)); Self.Cursor := crDefault; if (bSizing) then SendMessage(Self.Handle, WM_SYSCOMMAND, WPARAM(SC_MOVE or 8), 0); end; end; procedure TApp_LenZoom.FormMouseDown(Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Integer); begin if (Button = mbRight) then begin //マウスジェスチャー F_ptGesture := Point(X, Y); end else if (Button = mbLeft) then begin //移動 F_ptMvClientMousePos := gfnptClientMousePosGet(Handle); if (actCapture_Fixed.Checked) and not(actCapture_Pause.Checked) //一時停止ではない and not(PtInRect(gfnrcRectShift(F_rcInfo, Point(0, 0)), F_ptMvClientMousePos)) //情報表示領域ではない // and not(actCapture_Lupe.Checked and actCapture_Lupe.Enabled) //ルーペモードではない and (Self.Cursor = crDefault) then begin //ポイント移動開始 SetCaptureControl(Self); F_bIsMoving := True; F_ptMvMousePos := F_rDispInfo.ptMousePos; end else if (gfnbKeyState(VK_CONTROL)) then begin //何もしないがMouseUpメッセージを得るために↓の処理には入らない end else if not(Windows.IsZoomed(Handle)) then begin //つかんで移動 //最大化しても移動できてしまったのでそれへの対処 F_MouseResize(X, Y, (ssLeft in Shift)); end; end; end; procedure TApp_LenZoom.FormMouseMove(Sender: TObject; Shift: TShiftState; X, Y: Integer); var lpt_Pos: TPoint; lr_Monitor: TMyMonitorPos; begin if (F_bIsMoving) then begin if (ssLeft in Shift) and not(F_bThrough) then begin F_bThrough := True; lpt_Pos := Point( gfniNumLimit(gfniRound((F_ptMvMousePos.X * F_iZoom + F_ptMvClientMousePos.X - X) / F_iZoom), MyMonitors.ScreenLeft, MyMonitors.ScreenBoundsRect.Right -1), gfniNumLimit(gfniRound((F_ptMvMousePos.Y * F_iZoom + F_ptMvClientMousePos.Y - Y) / F_iZoom), MyMonitors.ScreenTop, MyMonitors.ScreenBoundsRect.Bottom -1) ); F_rDispInfo.ptMousePos := lpt_Pos; lr_Monitor := gfnrScreenToMonitor(lpt_Pos); if (lr_Monitor.MonitorNum = 0) and (F_iMonitorNum > 0) //AIU then begin F_rDispInfo.ptMousePos.X := gfniNumLimit(F_rDispInfo.ptMousePos.X, MyMonitors[F_iMonitorNum -1].Left, MyMonitors[F_iMonitorNum -1].BoundsRect.Right -1); F_rDispInfo.ptMousePos.Y := gfniNumLimit(F_rDispInfo.ptMousePos.Y, MyMonitors[F_iMonitorNum -1].Top, MyMonitors[F_iMonitorNum -1].BoundsRect.Bottom -1); end else begin F_iMonitorNum := lr_Monitor.MonitorNum; end; DrawNow; Application.ProcessMessages; //余計なキューを捨てる F_bThrough := False; end; end else begin F_MouseResize(X, Y, (ssLeft in Shift)); end; end; //マウスアップ procedure TApp_LenZoom.FormMouseUp(Sender: TObject; Button: TMouseButton; Shift: TShiftState; X, Y: Integer); var lpt_Pos: TPoint; ls_Compas: WideString; begin if (Button = mbLeft) then begin ReleaseCapture; F_bIsMoving := False; if (actCapture_Pause.Checked or actCapture_Fixed.Checked) and (ssCtrl in Shift) and not(ssShift in Shift) then begin //[Ctrl]キーが押されていて[Shift]キーが押されていなければカーソル位置にキャプチャポイントをもっていく FormDblClick(nil); end; end else if (Button = mbRight) and ((F_ptGesture.X > 0) or (F_ptGesture.Y > 0)) then begin //マウスジェスチャー ls_Compas := gfnsCompasGet(F_ptGesture, Point(X, Y)); if (ls_Compas = '') then begin //いわゆる右クリック //ポップアップメニュー lpt_Pos := ClientToScreen(Point(X, Y)); mnuMain.Popup(lpt_Pos.X, lpt_Pos.Y); end else begin if (ls_Compas = '上') then begin F_ExecuteCmd(G_rMouseGesture.iCommand_Up); end else if (ls_Compas = '下') then begin F_ExecuteCmd(G_rMouseGesture.iCommand_Down); end else if (ls_Compas = '左') then begin F_ExecuteCmd(G_rMouseGesture.iCommand_Left); end else if (ls_Compas = '右') then begin F_ExecuteCmd(G_rMouseGesture.iCommand_Right); end; end; end; end; //------------------------------------------------------------------------------ procedure TApp_LenZoom.actNop(Sender: TObject); begin //ダミー end; //モニター間移動 procedure TApp_LenZoom.actMove_MonitorExecute(Sender: TObject); var lrc_Rect: TRect; begin if (gfnbKeyState(VK_SHIFT)) then begin //プライマリモニターの左上に移動。 SetBounds(0, 0, Width, Height); end else {if (gfnbKeyState(VK_CONTROL)) then} begin //モニター間移動。 lrc_Rect := MyMonitors[gfniNumLoop(MyMonitors.MonitorNum(Handle) +1, 1, MyMonitors.Count) -1].WorkareaRect; SetBounds(lrc_Rect.Left, lrc_Rect.Top, Width, Height); end; end; //カーソル移動 procedure TApp_LenZoom.actMove_LeftExecute(Sender: TObject); procedure lfn_CaptureMove(X, Y: Integer); begin if (actCapture_Fixed.Checked) then begin //定点キャプチャ if not(actCapture_Pause.Checked) then begin F_rDispInfo.ptMousePos := Point( gfniNumLimit(F_rDispInfo.ptMousePos.X + X, MyMonitors.ScreenLeft, MyMonitors.ScreenBoundsRect.Right -1), gfniNumLimit(F_rDispInfo.ptMousePos.Y + Y, MyMonitors.ScreenTop, MyMonitors.ScreenBoundsRect.Bottom -1) ); Timer_InfomationTimer(nil); DrawNow; end; end else if (actCapture_Lupe.Checked) then begin //ルーペモード Self.SetBounds(Self.Left + X, Self.Top + Y, Self.Width, Self.Height); end else begin //カーソル移動 SetCursorPos(F_rDispInfo.ptMousePos.X + X, F_rDispInfo.ptMousePos.Y + Y); end; end; var li_Move: Integer; begin if (gfnbKeyState(VK_SHIFT)) then begin li_Move := 10; end else begin li_Move := 1; end; if (Sender = actMove_Left) then begin lfn_CaptureMove(-li_Move, 0); { if (actCapture_Fixed.Checked) then begin lfn_CaptureMove(-li_Move, 0); end else begin //カーソル移動← SetCursorPos(F_rDispInfo.ptMousePos.X -li_Move, F_rDispInfo.ptMousePos.Y); end; } end else if (Sender = actMove_Right) then begin lfn_CaptureMove(li_Move, 0); { if (actCapture_Fixed.Checked) then begin lfn_CaptureMove(li_Move, 0); end else begin //カーソル移動→ SetCursorPos(F_rDispInfo.ptMousePos.X +li_Move, F_rDispInfo.ptMousePos.Y); end; } end else if (Sender = actMove_Up) then begin lfn_CaptureMove(0, -li_Move); { if (actCapture_Fixed.Checked) then begin lfn_CaptureMove(0, -li_Move); end else begin //カーソル移動↑ SetCursorPos(F_rDispInfo.ptMousePos.X, F_rDispInfo.ptMousePos.Y -li_Move); end; } end else if (Sender = actMove_Down) then begin lfn_CaptureMove(0, li_Move); { if (actCapture_Fixed.Checked) then begin lfn_CaptureMove(0, li_Move); end else begin //カーソル移動↓ SetCursorPos(F_rDispInfo.ptMousePos.X, F_rDispInfo.ptMousePos.Y +li_Move); end; } end; end; procedure TApp_LenZoom.ApplicationEvents1ShortCut(var Msg: TWMKey; var Handled: Boolean); begin if (Msg.CharCode = VK_MENU) then begin //[Alt]を殺す Handled := True; end; end; procedure TApp_LenZoom.actMenu_MainExecute(Sender: TObject); //メニューのポップアップ var lpt_Pos: TPoint; begin lpt_Pos := ClientToScreen(Point(0, 0)); mnuMain.Popup(lpt_Pos.X, lpt_Pos.Y); end; procedure TApp_LenZoom.actColor_InfoOnOffExecute(Sender: TObject); begin actColor_RGB.Checked := not( (actColor_RGB.Checked) and (actColor_HTML.Checked) and (actColor_COLORREF.Checked) ); actColor_HTML.Checked := actColor_RGB.Checked; actColor_COLORREF.Checked := actColor_RGB.Checked; FormResize(nil) end; procedure TApp_LenZoom.actPos_InfoOnOffExecute(Sender: TObject); begin actPos_Screen.Checked := not( (actPos_Screen.Checked) and (actPos_Client.Checked) and (actPos_User.Checked) ); actPos_Client.Checked := actPos_Screen.Checked; actPos_User.Checked := actPos_Screen.Checked; FormResize(nil) end; procedure TApp_LenZoom.actWinInfo_InfoOnOffExecute(Sender: TObject); begin actWinInfo_Handle.Checked := not( (actWinInfo_Handle.Checked) and (actWinInfo_ClassName.Checked) and (actWinInfo_Text.Checked) and (actWinInfo_WindowSize.Checked) and (actWinInfo_ClientSize.Checked) and (actWinInfo_Rect.Checked) and (actWinInfo_ExeName.Checked) ); actWinInfo_ClassName.Checked := actWinInfo_Handle.Checked; actWinInfo_Text.Checked := actWinInfo_Handle.Checked; actWinInfo_WindowSize.Checked := actWinInfo_Handle.Checked; actWinInfo_ClientSize.Checked := actWinInfo_Handle.Checked; actWinInfo_Rect.Checked := actWinInfo_Handle.Checked; actWinInfo_ExeName.Checked := actWinInfo_Handle.Checked; FormResize(nil); end; procedure TApp_LenZoom.actHelpExecute(Sender: TObject); begin gpcShowMessage(Self.Caption, Application.Title); end; //============================================================================== function TApp_LenZoom.F_LoadBin: Boolean; var li_Left, li_Top, li_Width, li_Height: Integer; begin Result := G_fnbSettingRead; //(G_rSettingInfo, G_rShortCutKeys, G_rMouseGesture); if not(Result) then begin Exit; end; with G_rSettingInfo do begin //[Zoom] //倍率の設定は最初にやっておく F_iZoomIndex := gfniNumLimit(iZoomIndex, 0, mniZoom.Count -1); actZoomExecute(mniZoom.Items[F_iZoomIndex].Action); //[Grid] //actGrid_DispExecuteを呼ばないのでnotで反転させる必要はない actGrid_Disp.Checked := (iGridFlag and G_ciFLGGRID_DISP) = G_ciFLGGRID_DISP; actGrid_SelColor.Tag := clGridColor; actGrid_SelSubColor.Tag := clSubGridColor; //グリッド色 TAction(mniGrid.Items[iGridIndex].Action).Checked := True; actGrid_ColorExecute(mniGrid.Items[iGridIndex].Action); //サブグリッド色 //サブメニュー iSubGridIndex := iSubGridIndex + (mniGrid_LineSubGrid.MenuIndex +1); TAction(mniGrid.Items[iSubGridIndex].Action).Checked := True; actGrid_SubBlueExecute(mniGrid.Items[iSubGridIndex].Action); //[Color] actColor_RGB.Checked := (iColorFlag and G_ciFLGCOLOR_RGB) = G_ciFLGCOLOR_RGB; actColor_HTML.Checked := (iColorFlag and G_ciFLGCOLOR_HTML) = G_ciFLGCOLOR_HTML; actColor_COLORREF.Checked := (iColorFlag and G_ciFLGCOLOR_REF) = G_ciFLGCOLOR_REF; //[Position] actPos_Screen.Checked := (iPosFlag and G_ciFLGPOS_SCREEN) = G_ciFLGPOS_SCREEN; actPos_Client.Checked := (iPosFlag and G_ciFLGPOS_CLIENT) = G_ciFLGPOS_CLIENT; actPos_User.Checked := (iPosFlag and G_ciFLGPOS_USER) = G_ciFLGPOS_USER; F_rDispInfo.ptUserPos.X := gfniNumLimit(ptUserPos.X, 0, MyMonitors.ScreenWidth); F_rDispInfo.ptUserPos.Y := gfniNumLimit(ptUserPos.Y, 0, MyMonitors.ScreenHeight); //[WindowInfo] actWinInfo_Handle.Checked := (iWInfoFlag and G_ciFLGWINFO_HANDLE) = G_ciFLGWINFO_HANDLE; actWinInfo_ClassName.Checked := (iWInfoFlag and G_ciFLGWINFO_CNAME) = G_ciFLGWINFO_CNAME; actWinInfo_Text.Checked := (iWInfoFlag and G_ciFLGWINFO_TEXT) = G_ciFLGWINFO_TEXT; actWinInfo_WindowSize.Checked := (iWInfoFlag and G_ciFLGWINFO_WSIZE) = G_ciFLGWINFO_WSIZE; actWinInfo_ClientSize.Checked := (iWInfoFlag and G_ciFLGWINFO_CSIZE) = G_ciFLGWINFO_CSIZE; actWinInfo_Rect.Checked := (iWInfoFlag and G_ciFLGWINFO_RECT) = G_ciFLGWINFO_RECT; actWinInfo_ExeName.Checked := (iWInfoFlag and G_ciFLGWINFO_EXENAME) = G_ciFLGWINFO_EXENAME; //[Option] actOpt_StayOnTop.Checked := not((iOptFlag and G_ciFLGOPT_STAYONTOP) = G_ciFLGOPT_STAYONTOP); actOpt_BigFont.Checked := (iOptFlag and G_ciFLGOPT_BIGFONT) = G_ciFLGOPT_BIGFONT; actOpt_NoSelfCapture.Checked := (iOptFlag and G_ciFLGOPT_NOSELF) = G_ciFLGOPT_NOSELF; actOpt_SmoothCapture.Checked := (iOptFlag and G_ciFLGOPT_SMOOTH) = G_ciFLGOPT_SMOOTH; actOpt_StayOnTopExecute (actOpt_StayOnTop); actOpt_BigFontExecute (actOpt_BigFont); actOpt_NoSelfCaptureExecute(actOpt_NoSelfCapture); actOpt_SmoothCaptureExecute(actOpt_SmoothCapture); //[Capture] actCapture_Lupe.Checked := (iCaptureFlag and G_ciFLGCAPTURE_LUPE) = G_ciFLGCAPTURE_LUPE; actCapture_Fixed.Checked := (iCaptureFlag and G_ciFLGCAPTURE_FIXED) = G_ciFLGCAPTURE_FIXED; if (actCapture_Lupe.Checked) then begin actCapture_LupeExecute(actCapture_Lupe); end else if (actCapture_Fixed.Checked) then begin // actCapture_FixedExecute(actCapture_Fixed); F_rDispInfo.ptMousePos := ptCaptruePos; end; //[Bounds] if (gfniRectWidth (rcRect) <= FciMINSIZE) or (gfniRectHeight(rcRect) <= FciMINSIZE) then begin li_Width := Width; li_Height := Height; end else begin //[Bounds] li_Width := gfniRectWidth(rcRect); li_Height := gfniRectHeight(rcRect); end; if (gfnbKeyState(VK_SHIFT)) then begin //Shiftキーを押しながら起動で(0,0)に移動 li_Left := 0; li_Top := 0; end else begin li_Left := rcRect.Left; li_Top := rcRect.Top; end; SetBounds(li_Left, li_Top, li_Width, li_Height); if not(gfnbKeyState(VK_CONTROL)) then begin //画面内に収まるように調整 //ただし情報エリアは画面外にはみ出して起動する場合あり。 MyMonitors.SetBounds(Self); end else begin //Ctrlキーを押して起動した場合は調整はせず設定ファイルに従った位置と大きさで起動 //何らかの意図で画面外に起動させたい場合にも対応。 end; end; end; procedure TApp_LenZoom.F_SaveBin; var i: Integer; begin with G_rSettingInfo do begin rcRect := Self.BoundsRect; Dec(rcRect.Bottom, gfniRectHeight(F_rcInfo)); //[Zoom] iZoomIndex := F_iZoomIndex; //[Grid] iGridFlag := 0; if (actGrid_Disp.Checked) then begin iGridFlag := iGridFlag or G_ciFLGGRID_DISP; end; iGridIndex := mniGrid_Gray.MenuIndex; for i := mniGrid_LineGrid.MenuIndex +1 to mniGrid_LineSubGrid.MenuIndex -1 do begin if (mniGrid.Items[i].Checked) then begin iGridIndex := i; Break; end; end; //選択されているサブグリッドメニュー iSubGridIndex := mniGrid_SubBlue.MenuIndex; for i := mniGrid_LineSubGrid.MenuIndex +1 to mniGrid.Count -1 do begin if (mniGrid.Items[i].Checked) then begin iSubGridIndex := i; Break; end; end; iSubGridIndex := iSubGridIndex - (mniGrid_LineSubGrid.MenuIndex +1); //選択色 clGridColor := actGrid_SelColor.Tag; clSubGridColor := actGrid_SelSubColor.Tag; //[Color] iColorFlag := 0; if (actColor_RGB.Checked) then begin iColorFlag := iColorFlag or G_ciFLGCOLOR_RGB; end; if (actColor_HTML.Checked) then begin iColorFlag := iColorFlag or G_ciFLGCOLOR_HTML; end; if (actColor_COLORREF.Checked) then begin iColorFlag := iColorFlag or G_ciFLGCOLOR_REF; end; //[Position] iPosFlag := 0; if (actPos_Screen.Checked) then begin iPosFlag := iPosFlag or G_ciFLGPOS_SCREEN; end; if (actPos_Client.Checked) then begin iPosFlag := iPosFlag or G_ciFLGPOS_CLIENT; end; if (actPos_User.Checked) then begin iPosFlag := iPosFlag or G_ciFLGPOS_USER; end; ptUserPos := F_rDispInfo.ptUserPos; //[WindowsInfo] iWInfoFlag := 0; if (actWinInfo_Handle.Checked) then begin iWInfoFlag := iWInfoFlag or G_ciFLGWINFO_HANDLE; end; if (actWinInfo_ClassName.Checked) then begin iWInfoFlag := iWInfoFlag or G_ciFLGWINFO_CNAME; end; if (actWinInfo_Text.Checked) then begin iWInfoFlag := iWInfoFlag or G_ciFLGWINFO_TEXT; end; if (actWinInfo_WindowSize.Checked) then begin iWInfoFlag := iWInfoFlag or G_ciFLGWINFO_WSIZE; end; if (actWinInfo_ClientSize.Checked) then begin iWInfoFlag := iWInfoFlag or G_ciFLGWINFO_CSIZE; end; if (actWinInfo_Rect.Checked) then begin iWInfoFlag := iWInfoFlag or G_ciFLGWINFO_RECT; end; if (actWinInfo_ExeName.Checked) then begin iWInfoFlag := iWInfoFlag or G_ciFLGWINFO_EXENAME; end; //[Option] iOptFlag := 0; if (actOpt_StayOnTop.Checked) then begin iOptFlag := iOptFlag or G_ciFLGOPT_STAYONTOP; end; if (actOpt_BigFont.Checked) then begin iOptFlag := iOptFlag or G_ciFLGOPT_BIGFONT; end; if (actOpt_NoSelfCapture.Checked) then begin iOptFlag := iOptFlag or G_ciFLGOPT_NOSELF; end; if (actOpt_SmoothCapture.Checked) then begin iOptFlag := iOptFlag or G_ciFLGOPT_SMOOTH; end; //[Capture] iCaptureFlag := 0; if (actCapture_Lupe.Checked) then begin iCaptureFlag := G_ciFLGCAPTURE_LUPE; end else if (actCapture_Fixed.Checked) then begin iCaptureFlag := G_ciFLGCAPTURE_FIXED; end; ptCaptruePos := F_rDispInfo.ptMousePos; end; G_pcSettingWrite; //(G_rSettingInfo, G_rShortCutKeys, G_rMouseGesture); end; end.