У меня есть 2 монитора, и мне нужно сохранить позицию формы, и она должна отображаться на экране, где она была закрыта.
Может кто-нибудь предложить, как получить экран, на котором он находится, и на загрузке формы показать его на экране, где форма была закрыта?
Настройки, которые я сохраняю в реестре.
Самый простой способ - вызвать функцию GetWindowPlacement
. Это возвращает структуру WINDOWPLACEMENT
, которая содержит информацию о координатах окна на экране.
Использование этой функции вместо свойства Form.Location
решает проблемы, с которыми вы столкнетесь с несколькими мониторами, сведенными к минимуму окнами, странно расположенными панелями задач и т.д.
Маршрутом атаки будет вызов функции GetWindowPlacement
при закрытии вашего приложения, сохранение местоположения окна в реестре (или там, где вы его храните) - реестр больше не является рекомендуемым местом для сохранения состояние приложения), а затем, когда ваше приложение повторно открывается, вызывая соответствующую функцию SetWindowPlacement
, чтобы восстановить окно до его предыдущей позиции.
Так как это нативные функции, открытые с помощью API Win32, и вы работаете на С#, вам нужно вызвать их через P/Invoke. Вот требуемые определения (для организационных целей я рекомендую разместить их в статическом классе с именем NativeMethods
):
[StructLayout(LayoutKind.Sequential)]
struct POINT
{
public int X;
public int Y;
}
[StructLayout(LayoutKind.Sequential)]
struct RECT
{
public int left;
public int top;
public int right;
public int bottom;
}
[Serializable]
[StructLayout(LayoutKind.Sequential)]
struct WINDOWPLACEMENT
{
public int length;
public int flags;
public int showCmd;
public POINT ptMinPosition;
public POINT ptMaxPosition;
public RECT rcNormalPosition;
}
[DllImport("user32", SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool GetWindowPlacement(IntPtr hWnd, ref WINDOWPLACEMENT lpwndpl);
[DllImport("user32", SetLastError = true)]
[return: MarshalAs(UnmanagedType.Bool)]
static extern bool SetWindowPlacement(IntPtr hWnd, ref WINDOWPLACEMENT lpwndpl);
Чтобы получить текущую позицию вашего окна (что вы будете делать, когда ваше приложение закрывается), используйте этот код:
WINDOWPLACEMENT wp = new WINDOWPLACEMENT();
wp.length = Marshal.SizeOf(wp);
GetWindowPlacement(MyForm.Handle, ref wp);
Напомним, что я упоминал, что реестр больше не является рекомендуемым местом для сохранения состояния приложения. Поскольку вы работаете в .NET, у вас есть гораздо более мощные и универсальные опции. А поскольку класс WINDOWPLACEMENT
, объявленный выше, помечен как [Serializable]
, было бы очень легко сериализовать эту информацию в настройках , а затем перезагрузите его при следующем открытии.
Я реализовал подобную функциональность много раз. Все, что вам нужно сделать, это сохранить свойства Form.WindowState
, Form.Size
и Form.Loaction
, когда форма закрыта и восстановить их при открытии формы.