AutoHotKeyで、ウィンドウを瞬間移動してみた(マルチモニタ対応)。

 ウィンドウを、いちいちマウスで移動するのが面倒だったので、アクティブなウィンドウを移動するAHK作った。
 デスクトップを3*3(右/中央/左、上/中/下)に区切って、ウィンドウを指定したデスクトップ淵に合わせる。マルチモニタ対応。

WinMoveG9(MntIdx = 0, MoveArea = 7) {
/*
 MntIdx : 異動先となるモニタ。デフォルトは0(移動しない)。
 MoveArea : 移動先となるグリッド(位置はテンキー参照)。デフォルトは7(左上)。
*/
  WinGet,WinId, ID, A
  WinGetPos, WinX, WinY, WinW, WinH, ahk_id %WinId%
  if MntIdx
    SysGet, Mnt, MonitorWorkArea, %MntIdx%
  else {
    WinYC := WinH // 2 + WinY, WinXC := WinW // 2 + WinX
    MntNum := 2 ; 有効なモニタ数(頻繁に変更するなら↓をアンコメント)
    ;~ SysGet, MntNum, 80
    Loop, %MntNum%
    {
      SysGet, Mnt, MonitorWorkArea, %A_Index%
      if (MntTop < WinYC) && (WinYC < MntBottom) && (MntLeft < WinXC) && (WinXC < MntRight)
        break
    }
  }

  if (7 == MoveArea || 4 == MoveArea || 1 == MoveArea)
    MoveX := MntLeft
  else if (8 == MoveArea || 5 == MoveArea || 2 == MoveArea)
    MoveX := (MntRight - MntLeft - WinW) / 2 + MntLeft
  else  ; if (9 == MoveArea || 6 == MoveArea || 3 == MoveArea)
    MoveX := MntRight - WinW

  if (7 == MoveArea || 8 == MoveArea || 9 == MoveArea)
    MoveY := MntTop
  else if (4 == MoveArea || 5 == MoveArea || 6 == MoveArea)
    MoveY := (MntBottom - MntTop - WinH) / 2 + MntTop
  else ; if (1 == MoveArea || 2 == MoveArea || 3 == MoveArea)
    MoveY := MntBottom - WinH

  WinMove, ahk_id %WinId%, , %MoveX%, %MoveY%
}

#Numpad1::WinMoveG9(0, 1)
#Numpad2::WinMoveG9(0, 2)
#Numpad3::WinMoveG9(0, 3)
#Numpad4::WinMoveG9(0, 4)
#Numpad5::WinMoveG9(0, 5)
#Numpad6::WinMoveG9(0, 6)
#Numpad7::WinMoveG9(0, 7)
#Numpad8::WinMoveG9(0, 8)
#Numpad9::WinMoveG9(0, 9)

#1::
  WinMoveG9(1)
return
#2::
  WinMoveG9(2)
return

#c::
  WinMoveG9(0, 5)
return

 例えば、Win+NumPad7で今いるモニタの基準位置(左上)に、Win+NumPad3なら今いるモニタの右下に移動。Win+NumPad5かWin+Cで画面中央に移動。Win+1でモニタ1の基準位置へ移動。


[PR]
by lordnoesis | 2013-01-31 21:00 | Trackback | Comments(1)

MouseGesture.ahkで"半画面"してみた。5

 なんとなくほぼゼロから作り直してマルチモニタとタスクバーに対応させてみたver.2。
 マルチモニタ対応なら簡単かなーと思ったら、タスクバー避ける方が簡単だった罠。

 改めて説明すると、これはWindows7のAeroSnapのように「モニタの左右どちらかに最大化」できる「MouseGesture.ahk」用のジェスチャースクリプト。ウィンドウのタイトルバーをミドルクリック(ホイールクリック)することで"半画面化"でき、その状態でさらに同じ操作をすると逆側に移動する。
 ver.2からはマルチモニタ環境に対応。「タスクバーを自動的に隠す」設定でなくとも問題なく半画面化可能。そのほか、解像度によっては半画面化の切り替えができない問題とかも改善。

[TitleBar]
Custom=MG_HitTest()="Caption"

[MB__]
G=MB__
TitleBar=WinActivate【TAB】WinHC := MG_WinH() // 2 + MG_WinY()【TAB】WinWC := MG_WinW() // 2 + MG_WinX()【TAB】【TAB】Loop, 3【TAB】{【TAB】【TAB】Cnt := A_Index - 1【TAB】【TAB】SysGet, Mnt, MonitorWorkArea, %Cnt%【TAB】【TAB】if ((MntTop < WinHC) && (WinHC < MntBottom) && (MntLeft < WinWC) && (WinWC < MntRight))【TAB】【TAB】【TAB】break【TAB】}【TAB】MntWC := (MntRight - MntLeft) // 2【TAB】【TAB】offset := 0【TAB】if (MG_Win("MinMax") == 1) {【TAB】【TAB】if (MG_WinW() == MntWC) {【TAB】【TAB】【TAB】if (MG_WinX() == MntLeft + MntWC) {【TAB】【TAB】【TAB】【TAB】offset := 0 - MntWC【TAB】【TAB】【TAB】} else {【TAB】【TAB】【TAB】【TAB】if (MG_WinX() == MntLeft) {【TAB】【TAB】【TAB】【TAB】【TAB】offset := MntWC【TAB】【TAB】【TAB】【TAB】}【TAB】【TAB】【TAB】}【TAB】【TAB】}【TAB】} else {【TAB】【TAB】WinMaximize【TAB】}【TAB】【TAB】if (MG_WinY() < MntTop) {【TAB】【TAB】WinTY := MntTop【TAB】【TAB】WinTH := MntBottom - MntTop【TAB】} else {【TAB】【TAB】WinTY := MG_WinY()【TAB】【TAB】WinTH := MntBottom - MG_WinY()【TAB】}【TAB】【TAB】if (WinWC - MntLeft + offset >= MntWC) {【TAB】【TAB】WinMove, A, , MntLeft + MntWC, WinTY, MntWC, WinTH【TAB】} else {【TAB】【TAB】WinMove, A, , MntLeft, WinTY, MntWC, WinTH【TAB】}
CWEditor=Send,{LButton}{AppsKey}{Down}{Enter}{BS}

 実際やってみたらMonitorWorkArea使うだけでよかったので、もっと早くやっとけばよかったか。しかし、大して機能は増えてないくせに、処理とスクリプト量は増えたなぁ……。

 モニタが4つ以上ある環境では"Loop, 3"の数字を増やす。別に数字なくても(無制限でも)いいはずなんだが、安全策で。


[PR]
by lordnoesis | 2011-03-17 10:54 | テクノロジ | Trackback | Comments(0)

MouseGesture.ahkで"半画面"してみた。4

 Windows7のAeroSnapにインスパイアされたスクリプトがWindows7で動かなかったので修正したver.1.2.1。
 本家のドラッグより、ミドルクリックだけのが簡単だよね!

 1.2との違いは間違いさがしに等しいというか、モニタサイズを取得してた部分を組み込み変数に変えただけ。7はモニタサイズの取得変えなきゃダメなのかー?とリファレンス見たら、プライマリモニタのサイズだけは調べなくても組み込み変数があったっつー……。
 単なるバグ修正だけなので、使い方とかは前のver.の説明を参照。

[TitleBar]
Custom=MG_HitTest()="Caption"

[MB__]
G=MB__
TitleBar=WinActivate【TAB】Mni1W := A_ScreenWidth / 2【TAB】【TAB】if (MG_Win("MinMax") = 1)【TAB】{【TAB】;if MG_WinH() > (A_ScreenHeight - MG_WinY())【TAB】【TAB】【TAB】WinY := A_ScreenHeight - MG_WinY()【TAB】;else【TAB】;WinY :=【TAB】【TAB】if ((MG_WinX() = 0) & (MG_WinW() = Mni1W))【TAB】【TAB】【TAB】WinMove, A, , Mni1W, , Mni1W, WinY【TAB】【TAB】else if ((MG_WinX() = Mni1W) & (MG_WinW() = Mni1W))【TAB】【TAB】【TAB】WinMove, A, , 0, , Mni1W, WinY【TAB】【TAB】else if (MG_WinX() + MG_WinW() / 2 >= Mni1W)【TAB】【TAB】【TAB】WinMove, A, , Mni1W, , Mni1W, WinY【TAB】【TAB】else【TAB】【TAB】【TAB】WinMove, A, , 0, , Mni1W, WinY【TAB】} else {【TAB】【TAB】if (MG_WinX() + MG_WinW() /2 >= Mni1W)【TAB】【TAB】{【TAB】【TAB】【TAB】WinMaximize【TAB】【TAB】【TAB】WinMove, A, , Mni1W, , Mni1W, 【TAB】【TAB】} else {【TAB】【TAB】【TAB】WinMaximize【TAB】【TAB】【TAB】WinMove, A, , 0, , Mni1W, 【TAB】【TAB】}【TAB】}

 いいかげんちゃんとマルチモニタ環境に対応させようかしらん。


[PR]
by lordnoesis | 2011-02-23 22:37 | テクノロジ | Trackback | Comments(0)

MouseGesture.ahkで"半画面"してみた。3

 Windows7のスナップ機能の「モニタの左右に最大化」にインスパイアされたMouseGesture.ahk向けのスクリプトを、さらに改良してみた。ver.1.2くらいかな?

 改めて説明すると、ウィンドウのタイトルバーをミドルクリックすることで、モニタの左右半分に最大化する。MouseGesture.ahkでインポートして利用する。
 詳しくは前のver.の説明を参照してもらうとして。改良点は、ウィンドウの縦位置を考慮するようになったこと。

 まず前提として、デスクトップはプライマリモニタの左上を始点(0,0)として、横軸(X)と縦軸(Y)による2次元座標で管理されている。以前のver.を実行すると、ウィンドウの上端は必ずY:0にあった。このver.ではそれを改め、最大化後(あるいは左右切り替え時)のY座標を維持するようになった。

 ウィンドウの中には最大化しても、他のウィンドウ(代表的なのはタスクバーだ)を避けるために、上下左右に余白を残すことがある。だから、このver.では最大化した時点を基準として、上下の縦座標(余白)を維持するようになった。要するに、ウィンドウを半最大化した場合でも、問題が起こりにくくなったということ。

 半最大化した状態で左右を切り替えた時も同様だ。ただし、他の手段で移動するなどして、ウィンドウの下端がプライマリモニタの領域からはみ出していた場合、領域内に収めるためにウィンドウの高さを縮める。セカンダリモニタが下にあって困ってなくても問答無用。またタスクバーを考慮しないので、タスクバーがにかぶってしまうことも。仕様である。


[TitleBar]
Custom=MG_HitTest()="Caption"

[MB__]
G=MB__
TitleBar=WinActivate【TAB】SysGet, Mni1, Monitor,1【TAB】Mni1W := Mni1Right / 2【TAB】if (MG_Win("MinMax") = 1)【TAB】{【TAB】【TAB】if MG_WinH() > (Mni1Bottom - MG_WinY())【TAB】【TAB】【TAB】WinY := Mni1Bottom - MG_WinY()【TAB】【TAB】else【TAB】【TAB】【TAB】WinY :=【TAB】【TAB】if ((MG_WinX() = 0) & (MG_WinW() = Mni1W))【TAB】【TAB】【TAB】WinMove, A, , Mni1W, , Mni1W, WinY【TAB】【TAB】else if ((MG_WinX() = Mni1W) & (MG_WinW() = Mni1W))【TAB】【TAB】【TAB】WinMove, A, , 0, , Mni1W, WinY【TAB】【TAB】else if (MG_WinX() + MG_WinW() / 2 >= Mni1W)【TAB】【TAB】【TAB】WinMove, A, , Mni1W, , Mni1W, WinY【TAB】【TAB】else【TAB】【TAB】【TAB】WinMove, A, , 0, , Mni1W, WinY【TAB】} else {【TAB】【TAB】if (MG_WinX() + MG_WinW() /2 >= Mni1W)【TAB】【TAB】{【TAB】【TAB】【TAB】WinMaximize【TAB】【TAB】【TAB】WinMove, A, , Mni1W, , Mni1W, 【TAB】【TAB】} else {【TAB】【TAB】【TAB】WinMaximize【TAB】【TAB】【TAB】WinMove, A, , 0, , Mni1W, 【TAB】【TAB】}【TAB】}

 すでに通常の最大化を行った状態でタイトルバーをミドルクリックをした場合、右側に半最大化される。これを左側にする場合else if (MG_WinX() + MG_WinW() / 2 >= Mni1W + 1)+1を外す。
 左右切り替え時に、ウィンドウ下端を領域内に収めるだけではなく、余白をなくして領域の限界まで広げたい場合、if MG_WinH() > (Mni1Bottom - MG_WinY())と、そのあとに出てくるelseWinY :=を削除かコメントアウト。

 メリットとデメリットを考慮して、相変わらず「マルチモニタ非対応」「タスクバー無視」。タスクバーくらいは対応してもいいかなって気もするが、自分(タスクバーは隠す派)じゃ困ってないしなー。


[PR]
by lordnoesis | 2010-01-28 00:12 | テクノロジ | Trackback | Comments(0)

MouseGesture.ahkで"半画面"してみた。2.3

 前回のスクリプトを少し強化してみた。ものをさらに少し改良してみた。しかも3回ほど。要するにver.1.1c?

 タイトルバーを中クリックすると、プライマリモニタの左右どちらかに"半最大化"するMouseGesture.ahkスクリプト。"どちらか"はウィンドウの状態によって異なる。ウィンドウが通常の最大化状態ならば左側に、"半最大化"しており定位置にあるならその反対側に。それらのどれでもなければ、ウィンドウの中心座標が画面中央より左側なら左、右側なら右に"半最大化"される。
 ま、要するに左右切り替えれるようにしたってだけね。

[TitleBar]
Custom=MG_HitTest()="Caption"
[MB__]
G=MB__
TitleBar=WinActivate【TAB】SysGet, Mni1, Monitor,1【TAB】Mni1W := Mni1Right / 2【TAB】if (MG_Win("MinMax") = 1)【TAB】{【TAB】【TAB】if ((MG_WinX() = 0) & (MG_WinW() = Mni1W))【TAB】【TAB】【TAB】WinMove, A, , Mni1W, 0, Mni1W, Mni1Bottom【TAB】【TAB】else if ((MG_WinX() = Mni1W) & (MG_WinW() = Mni1W))【TAB】【TAB】【TAB】WinMove, A, , 0, 0, Mni1W, Mni1Bottom【TAB】【TAB】else if (MG_WinX() + MG_WinW() / 2 >= Mni1W + 1)【TAB】【TAB】【TAB】WinMove, A, , Mni1W, 0, Mni1W, Mni1Bottom【TAB】【TAB】else【TAB】【TAB】【TAB】WinMove, A, , 0, 0, Mni1W, Mni1Bottom【TAB】} else {【TAB】【TAB】if (MG_WinX() + MG_WinW() /2 >= Mni1W)【TAB】【TAB】{【TAB】【TAB】【TAB】WinMaximize【TAB】【TAB】【TAB】WinMove, A, , Mni1W, 0, Mni1W, Mni1Bottom【TAB】【TAB】} else {【TAB】【TAB】【TAB】WinMaximize【TAB】【TAB】【TAB】WinMove, A, , 0, 0, Mni1W, Mni1Bottom【TAB】【TAB】}【TAB】}

 通常最大化時のミドルクリックを左側"半最大化"ではなく右側"半最大化"にするには、else if (MG_WinX() + MG_WinW() / 2 >= Mni1W + 1)の「+1」を外してください。


 相変わらずマルチモニタ実質非対応。ver.1の「右側にのみ"半最大化"可」っていうのもそうだったけど、"半最大化"したあと手動で動かせばいいよねっていう。

 そもそもMG.ahkは、プライマリより左/上にある(座標がマイナスになる)モニタでのタイトルバー検知に非対応っぽい?
 もしそれが可能で、スクリプトをマルチモニタに対応させるとしたら――SysGetでモニタ総数数えてループさせて、全モニタの領域サイズ取得して、ウィンドウの現在座標と比較して……? うーむ、ちょっと便利がすごく"重い"。

 あと、タスクバーを考慮してないので、「タスクバーを自動的に隠す」がONでないとウィンドウの一部がタスクバーにめり込みます。

 タスクバー考慮するなら、SysGetを「MonitorWorkArea」にして、WinGetPosで「ahk_class Shell_TrayWnd」=タスクバーの位置やサイズ測って、ウィンドウ座標に反映させて――わし、「隠す」だからいいや(ぐへ。


[PR]
by lordnoesis | 2008-12-22 07:41 | テクノロジ | Trackback | Comments(0)

MouseGesture.ahkで"半画面"してみた。

 Windows7のウィンドウ操作にインスパイアされて書いた、タイトルバーを中クリックすると、プライマリモニタの右半分に最大化するMouseGesture.ahkスクリプト。

[TitleBar]
Custom=MG_HitTest()="Caption"
[MB__]
G=MB__
TitleBar=WinMaximize【TAB】WinActivate【TAB】SysGet, Mni1, Monitor,1【TAB】Mni1W := Mni1Right/2【TAB】WinMove, A, , Mni1W, 0, Mni1W, Mni1Bottom

名称未定っぽい。:MouseGesture.ahkで"半画面"してみた。2 -- 少し改良。"半最大化"後、左右切り替えれるように。


[PR]
by lordnoesis | 2008-11-20 10:48 | テクノロジ | Trackback | Comments(0)
ブログトップ | ファンになる