mirror of
https://github.com/kangyu-california/PersistentWindows.git
synced 2025-05-11 21:15:38 +02:00
experiment to move taskbar
This commit is contained in:
parent
523d4ba0e3
commit
7cf8a152fc
3 changed files with 163 additions and 4 deletions
|
@ -10,6 +10,10 @@ namespace Ninjacrab.PersistentWindows.Common.Models
|
|||
public uint ProcessId { get; set; }
|
||||
public string ClassName { get; set; }
|
||||
public string ApplicationName { get; set; }
|
||||
|
||||
public bool IsTaskbar { get; set; }
|
||||
public Shell32.APP_BAR_DATA TaskBarPos { get; set; }
|
||||
|
||||
public RECT ScreenPosition { get; set; }
|
||||
public WindowPlacement WindowPlacement { get; set; }
|
||||
public bool NeedUpdateWindowPlacement { get; set; } //non-persistent data used for tmp argument passing only
|
||||
|
|
|
@ -64,6 +64,20 @@ namespace Ninjacrab.PersistentWindows.Common
|
|||
#endif
|
||||
public void Start()
|
||||
{
|
||||
/*
|
||||
RECT screenPosition = new RECT();
|
||||
//IntPtr hTaskMan = User32.FindWindowA(null, "Untitled - Notepad");
|
||||
IntPtr hTaskMan = User32.FindWindowA(null, "Task Manager");
|
||||
User32.GetWindowRect(hTaskMan, ref screenPosition);
|
||||
User32.SetCursorPos(screenPosition.Left + 200, screenPosition.Top + 20);
|
||||
User32.SetForegroundWindow(hTaskMan);
|
||||
User32.SetActiveWindow(hTaskMan);
|
||||
User32.mouse_event(MouseAction.MOUSEEVENTF_LEFTDOWN, 0, 0, 0, UIntPtr.Zero);
|
||||
Thread.Sleep(1000); // wait to be activated
|
||||
User32.SetCursorPos(screenPosition.Left + 200, screenPosition.Top - 100);
|
||||
User32.mouse_event(MouseAction.MOUSEEVENTF_LEFTUP, 0, 0, 0, UIntPtr.Zero);
|
||||
*/
|
||||
|
||||
monitorApplications = new Dictionary<string, Dictionary<string, ApplicationDisplayMetrics>>();
|
||||
databaseLock = new object();
|
||||
validDisplayKeyForCapture = GetDisplayKey();
|
||||
|
@ -406,6 +420,10 @@ namespace Ninjacrab.PersistentWindows.Common
|
|||
{
|
||||
monitorApplications[displayKey].Add(curDisplayMetrics.Key, curDisplayMetrics);
|
||||
}
|
||||
else if (curDisplayMetrics.IsTaskbar)
|
||||
{
|
||||
monitorApplications[displayKey][curDisplayMetrics.Key].TaskBarPos = curDisplayMetrics.TaskBarPos;
|
||||
}
|
||||
else
|
||||
{
|
||||
monitorApplications[displayKey][curDisplayMetrics.Key].WindowPlacement = curDisplayMetrics.WindowPlacement;
|
||||
|
@ -540,14 +558,16 @@ namespace Ninjacrab.PersistentWindows.Common
|
|||
private IEnumerable<SystemWindow> CaptureWindowsOfInterest()
|
||||
{
|
||||
return SystemWindow.AllToplevelWindows
|
||||
.Where(row => row.Parent.HWnd.ToInt64() == 0
|
||||
.Where(row =>
|
||||
{
|
||||
return row.Parent.HWnd.ToInt64() == 0
|
||||
//&& !string.IsNullOrEmpty(row.Title)
|
||||
//&& !row.Title.Equals("Program Manager")
|
||||
//&& !row.Title.Contains("Task Manager")
|
||||
//&& row.Position.Height != 0
|
||||
//&& row.Position.Width != 0
|
||||
&& row.Visible
|
||||
);
|
||||
&& row.Visible;
|
||||
});
|
||||
}
|
||||
|
||||
private bool IsWindowMoved(string displayKey, SystemWindow window, User32Events eventType, DateTime now, out ApplicationDisplayMetrics curDisplayMetrics)
|
||||
|
@ -559,10 +579,15 @@ namespace Ninjacrab.PersistentWindows.Common
|
|||
return false;
|
||||
}
|
||||
|
||||
bool isTaskBar = false;
|
||||
Shell32.APP_BAR_DATA abd = new Shell32.APP_BAR_DATA();
|
||||
if (window.ClassName.Contains("Shell_TrayWnd"))
|
||||
{
|
||||
// capture task bar
|
||||
int i = 0;
|
||||
isTaskBar = true;
|
||||
abd.cbSize = (uint)Marshal.SizeOf(abd);
|
||||
abd.hWnd = window.HWnd;
|
||||
Shell32.SHAppBarMessage(Shell32.ABM_GETTASKBARPOS, ref abd);
|
||||
}
|
||||
else if (string.IsNullOrEmpty(window.Title))
|
||||
{
|
||||
|
@ -597,11 +622,31 @@ namespace Ninjacrab.PersistentWindows.Common
|
|||
ClassName = window.ClassName,
|
||||
ProcessId = processId,
|
||||
|
||||
IsTaskbar = isTaskBar,
|
||||
TaskBarPos = abd,
|
||||
|
||||
WindowPlacement = windowPlacement,
|
||||
NeedUpdateWindowPlacement = false,
|
||||
ScreenPosition = screenPosition
|
||||
};
|
||||
|
||||
if (isTaskBar)
|
||||
{
|
||||
IntPtr hReBar = User32.FindWindowEx(hwnd, IntPtr.Zero, "ReBarWindow32", null);
|
||||
User32.GetWindowRect(hReBar, ref screenPosition);
|
||||
//User32.SetCursorPos(screenPosition.Left + 50, screenPosition.Top + 1650);
|
||||
User32.SetCursorPos(screenPosition.Left + 3, screenPosition.Top + 3);
|
||||
User32.SetForegroundWindow(hReBar);
|
||||
User32.SetActiveWindow(hReBar);
|
||||
User32.mouse_event(MouseAction.MOUSEEVENTF_LEFTDOWN,
|
||||
0, 0, 0, UIntPtr.Zero);
|
||||
Thread.Sleep(2000); // wait to be activated
|
||||
User32.SetCursorPos(screenPosition.Left + 200, - (screenPosition.Top + 3));
|
||||
User32.mouse_event(MouseAction.MOUSEEVENTF_LEFTUP,
|
||||
0, 0, 0, UIntPtr.Zero);
|
||||
|
||||
int i = 0;
|
||||
}
|
||||
bool moved = false;
|
||||
if (!monitorApplications[displayKey].ContainsKey(curDisplayMetrics.Key))
|
||||
{
|
||||
|
@ -622,6 +667,10 @@ namespace Ninjacrab.PersistentWindows.Common
|
|||
// when close/reopen session, OS/user may activate existing window (possibly with different position)
|
||||
// just ignore it
|
||||
}
|
||||
else if (isTaskBar)
|
||||
{
|
||||
return !prevDisplayMetrics.TaskBarPos.Equals(curDisplayMetrics.TaskBarPos);
|
||||
}
|
||||
else if (!prevDisplayMetrics.EqualPlacement(curDisplayMetrics))
|
||||
{
|
||||
/*
|
||||
|
@ -767,6 +816,7 @@ namespace Ninjacrab.PersistentWindows.Common
|
|||
{
|
||||
sWindows = CaptureWindowsOfInterest();
|
||||
}
|
||||
|
||||
foreach (var window in sWindows)
|
||||
{
|
||||
if (!window.IsValid() || string.IsNullOrEmpty(window.ClassName))
|
||||
|
@ -798,6 +848,40 @@ namespace Ninjacrab.PersistentWindows.Common
|
|||
}
|
||||
|
||||
bool success = true;
|
||||
if (curDisplayMetrics.IsTaskbar)
|
||||
{
|
||||
// simulate mouse drag, assuming taskbar is unlocked
|
||||
/*
|
||||
ControlGetPos x, y, w, h, MSTaskListWClass1, ahk_class Shell_TrayWnd
|
||||
MouseMove x+1, y+1
|
||||
MouseClickDrag Left, x+1, y+1, targetX, targetY, 10
|
||||
*/
|
||||
IntPtr hTaskBar = User32.FindWindowEx(hwnd, IntPtr.Zero, "MSTaskListWClass1", "Running applications");
|
||||
|
||||
/*
|
||||
Shell32.APP_BAR_DATA abd = prevDisplayMetrics.TaskBarPos;
|
||||
abd.cbSize = (uint)Marshal.SizeOf(abd);
|
||||
//abd.hWnd = window.HWnd;
|
||||
//abd.uEdge = Shell32.ABE_TOP;
|
||||
UIntPtr result = Shell32.SHAppBarMessage(Shell32.ABM_SETPOS, ref abd);
|
||||
Log.Info("Set TaskBar pos ({0} [{1}x{2}]-[{3}x{4}]) - {5}",
|
||||
window.Process.ProcessName,
|
||||
abd.rc.Left,
|
||||
abd.rc.Top,
|
||||
abd.rc.Width,
|
||||
abd.rc.Height,
|
||||
result);
|
||||
|
||||
User32.SetWindowPos(hwnd, IntPtr.Zero, abd.rc.Left, abd.rc.Top, abd.rc.Width, abd.rc.Height,
|
||||
//SWP_NOSENDCHANGING);
|
||||
SetWindowPosFlags.DoNotSendChangingEvent);
|
||||
|
||||
User32.ShowWindow(hwnd, 5); //SW_SHOW
|
||||
User32.UpdateWindow(hwnd);
|
||||
*/
|
||||
continue;
|
||||
}
|
||||
|
||||
if (restoreTimes >= MinRestoreTimes || curDisplayMetrics.NeedUpdateWindowPlacement)
|
||||
{
|
||||
// recover NormalPosition (the workspace position prior to snap)
|
||||
|
|
|
@ -49,6 +49,18 @@ namespace Ninjacrab.PersistentWindows.Common.WinApiBridge
|
|||
WINEVENT_INCONTEXT = 0x0004
|
||||
}
|
||||
|
||||
public enum MouseAction : uint
|
||||
{
|
||||
MOUSEEVENTF_ABSOLUTE = 0x8000,
|
||||
|
||||
MOUSEEVENTF_LEFTDOWN = 0x0002,
|
||||
MOUSEEVENTF_LEFTUP = 0x0004,
|
||||
MOUSEEVENTF_RIGHTDOWN = 0x0008,
|
||||
MOUSEEVENTF_RIGHTUP = 0x0010,
|
||||
|
||||
MOUSEEVENTF_MOVE = 0x0001,
|
||||
}
|
||||
|
||||
public class User32
|
||||
{
|
||||
#region EnumDisplayMonitors
|
||||
|
@ -96,10 +108,37 @@ namespace Ninjacrab.PersistentWindows.Common.WinApiBridge
|
|||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
public static extern bool IsWindow(IntPtr hWnd);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true)]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
public static extern bool ShowWindow(IntPtr hWnd, int cmd);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true)]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
public static extern bool UpdateWindow(IntPtr hWnd);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true)]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
public static extern bool IsTopLevelWindow(IntPtr hWnd);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true)]
|
||||
public static extern IntPtr FindWindowA(string lpClassName, string lpWindowName);
|
||||
|
||||
[DllImport("user32.dll", SetLastError = true)]
|
||||
public static extern IntPtr FindWindowEx(IntPtr parentHandle, IntPtr childAfter, string className, string windowTitle);
|
||||
|
||||
[DllImport("user32.dll")]
|
||||
public static extern void mouse_event(MouseAction dwFlags, int dx, int dy, uint dwData, UIntPtr dwExtraInfo);
|
||||
|
||||
[DllImport("user32.dll")]
|
||||
[return: MarshalAs(UnmanagedType.Bool)]
|
||||
public static extern bool SetCursorPos(int x, int y);
|
||||
|
||||
[DllImport("user32.dll")]
|
||||
public static extern bool SetForegroundWindow (IntPtr hWnd);
|
||||
|
||||
[DllImport("user32.dll", SetLastError=true)]
|
||||
public static extern IntPtr SetActiveWindow(IntPtr hWnd);
|
||||
|
||||
#region Hooks
|
||||
[DllImport("user32.dll")]
|
||||
public static extern IntPtr CallNextHookEx(IntPtr hhk, int nCode, IntPtr wParam, IntPtr lParam);
|
||||
|
@ -130,4 +169,36 @@ namespace Ninjacrab.PersistentWindows.Common.WinApiBridge
|
|||
|
||||
#endregion
|
||||
}
|
||||
|
||||
public class Shell32
|
||||
{
|
||||
[DllImport("Shell32.dll", CharSet = CharSet.Auto)]
|
||||
public static extern UIntPtr SHAppBarMessage(int dwMessage, ref APP_BAR_DATA abd);
|
||||
|
||||
public const int ABM_NEW = 0x00;
|
||||
public const int ABM_REMOVE = 0x01;
|
||||
public const int ABM_QUERYPOS = 0x02;
|
||||
public const int ABM_SETPOS = 0x03;
|
||||
public const int ABM_GETTASKBARPOS = 0x05;
|
||||
public const int ABM_SETAUTOHIDEBAR = 0x08;
|
||||
public const int ABM_SETSTATE = 0x0000000a;
|
||||
public const int ABE_LEFT = 0;
|
||||
public const int ABE_TOP = 1;
|
||||
public const int ABE_RIGHT = 2;
|
||||
public const int ABE_BOTTOM = 3;
|
||||
public const int ABS_AUTOHIDE = 0x01;
|
||||
public const int ABS_ALWAYSONTOP = 0x02;
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct APP_BAR_DATA
|
||||
{
|
||||
public uint cbSize;
|
||||
public IntPtr hWnd;
|
||||
public int uCallbackMessage;
|
||||
public int uEdge;
|
||||
public RECT rc;
|
||||
public IntPtr lParam;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue