Создать окно больше рабочего стола (разрешение экрана)

Мне нужно изменить размер окна больше, чем разрешение экрана или размер рабочего стола, программно и желательно вручную.

Поскольку MS-Windows XP/Vista запрещает размер окна больше размера экрана, есть ли у кого-нибудь идеи, как обойти это ограничение?

Я пытаюсь сделать эффект панорамирования на ноутбуке, чтобы было больше места для работы. У старого ноутбука с меньшим размером ЖК-дисплея была такая функция.

См. это: http://www.experts-exchange.com/OS/Microsoft_Operating_Systems/Windows/98/Q_21832063.html


person Community    schedule 15.01.2009    source источник


Ответы (9)


Если вы хотите изменить размер окна, которым вы не владеете (и без использования каких-либо ловушек), вы можете использовать Windows SetWindowPos API с установленным флагом SWP_NOSENDCHANGING (0x0400):

BOOL WINAPI SetWindowPos(
__in      HWND hWnd,
__in_opt  HWND hWndInsertAfter,
__in      int X,
__in      int Y,
__in      int cx,
__in      int cy,
__in      UINT uFlags // ** SWP_NOSENDCHANGING must be passed here **
);

Это предотвратит отправку сообщения WM_WINDOWPOSCHANGING, которое запускает ограничение WM_GETMINMAXINFO. Любой другой размер окна приведет к тому, что ограничение вернет окно к ограниченным размерам рабочего стола, поскольку сообщение будет отправлено, а размер окна будет применен.

Изменение размера окна (C#)

Ниже приведен небольшой пример программы, которая изменит размер Блокнота до 6000x6000 (измените строку «Без названия - Блокнот» на заголовок окна, размер которого вы хотите изменить, или возьмите имя окна и желаемый размер из аргументов командной строки)

namespace Example
{
 class Program
 {
  [DllImport("USER32.DLL")]
  public static extern IntPtr FindWindow(String className, String windowName);

  [DllImport("USER32.DLL", SetLastError = true)]
  public static extern bool SetWindowPos(IntPtr hWnd, IntPtr hWndInsertAfter, int left, int top, int width, int height, uint flags);

  static void Main(string[] args)
  {
   var TOP = new IntPtr(0);
   uint SHOWWINDOW = 0x0040, NOCOPYBITS = 0x0100, NOSENDCHANGING = 0x0400;
   var hwnd = FindWindow(null, "Untitled - Notepad");
   SetWindowPos(hwnd, TOP, 0, 0, 6000, 6000, NOCOPYBITS | NOSENDCHANGING | SHOWWINDOW);
  }
 }
}

Ограничения и предостережения

Этот подход, как правило, функционален, но существует ряд ограничений, которые могут препятствовать изменению размера окна или изменению размера каким-либо полезным способом.

Безопасность

Начиная с Windows Vista, Microsoft реализовала повышенную безопасность оконных сообщений. Исполняемый файл может взаимодействовать только с окнами в своем собственном контексте безопасности или ниже его. Например, чтобы изменить размер окна «Управление компьютером» (которое всегда работает с повышенными правами), эта программа также должна работать с повышенными правами.

Исправлены окна и логика компоновки

Размер окна может быть задан программой пассивно или активно. Окно с принудительно установленным размером пассивно устанавливает начальный размер и просто не предоставляет пользователю возможности изменить размер окна (например, нет управления захватом размера). Размер этих окон обычно можно изменить, отправив сообщение, как описано, но из-за отсутствия логики макета не будет показывать ничего, кроме дополнительной пустой клиентской области.

Windows с активным принудительным исполнением отслеживает размер, либо перехватывая сообщения Windows, такие как WM_SIZE, либо используя более сложную логику макета. Эти окна могут принимать сообщение, но ограничивают окончательный размер в своем собственном коде.

В любом случае в Windows с фиксированными размерами обычно отсутствует какая-либо логика компоновки, позволяющая использовать преимущества больших размеров, поэтому, даже если вы можете сделать это принудительно, изменение размера не дает никаких преимуществ.

WPF

Класс Window в WPF имеет класс HwndSource, который обрабатывает оконные сообщения, отправляемые в окно WPF. Частный метод LayoutFilterMessage перехватывает сообщения WM_SYSCOMMAND, WM_SIZING, WM_WINDOWPOSCHANGING и WM_SIZE. В этом случае сообщение WM_SIZE затем обрабатывается приватным Process_WM_SIZE, который фактически обходит флаг NOSENDCHANGING и изменяет RenderSize клиентской области WPF. Это часть общего процесса адаптации устаревших сообщений Win32 к событиям WPF.

Чистый эффект заключается в том, что размер окна Win32 host изменяется (если для параметра SizeToContent не установлено значение SizeToContent.WidthAndHeight), но область рендеринга WPF привязана к области рабочего стола, как если бы флаг NOSENDCHANGING не был установлен. Когда приведенный выше пример кода запускается для приложения WPF, вы можете увидеть окно 6000x6000 в Aero Peek на панели задач или предварительный просмотр окна в переключателе Windows-Tab, но вы также можете увидеть, что содержимое WPF и логика макета обрезаются до область рабочего стола. Таким образом, окно WPF похоже на активно применяемое окно, но вместо того, чтобы применять конкретный размер, принудительно применяется определенный максимум (для RenderArea) и не учитывается WM_WINDOWPOSCHANGING сообщение.

Если это ваше собственное приложение и вы размещаете WPF в окне Windows Forms (через ElementHost), вы можете изменить размер окна, и содержимое WPF будет учитывать Окно Windows Form рабочего стола.

Другие фреймворки

Другие фреймворки, такие как GTK и Qt, могут или не могут применять поведение и ограничения размера, и могут иметь различные обходные пути для преодоления этих ограничений. Любая данная программа может игнорировать, переписывать или обходить оконное сообщение, а инфраструктура может применять его во всем классе приложений, например, в WPF выше.

Подробнее об API SetWindowPos:

Справочный источник для Process_WM_SIZE метода HwndSource:

http://referencesource.microsoft.com/#PresentationCore/Core/CSharp/System/Windows/Interop/HwndSource.cs,da4aa32ad121c1b9,references

person Maxx Daymon    schedule 09.11.2011
comment
К сожалению, это то, что работает. Было бы здорово, если бы у Microsoft была какая-то опция реестра или что-то, что мы могли бы использовать, чтобы отключить ограничение размера окна по умолчанию. - person loop; 26.01.2013
comment
ух ты. Это действительно сработало! Почему у этого нет больше голосов? Это лучшее решение! - person Arsen Zahray; 06.06.2013
comment
Спасибо Арсен. Мало того, за него дважды проголосовали без комментариев, почему. Такова жизнь. По крайней мере, он все еще здесь для тех, кто в нем нуждается. - person Maxx Daymon; 14.06.2013
comment
Первоначальный спрашивающий Нельсон больше не является учетной записью. Вышеупомянутая тестовая учетная запись, возможно, является ОП, но из-за этого также нет принятого ответа. - person Maxx Daymon; 14.06.2013
comment
Проверено с Windows 10, кажется, больше не работает. :( - person Tyler Long; 16.12.2015
comment
@TylerLong Я только что добавил простой пример кода и протестировал его в Windows 10 (10586.29). Имейте в виду, что этот код должен будет выполняться в контексте безопасности любого окна или выше него, размер которого он пытается изменить. Например, если этот код работает от имени обычного пользователя, он не может изменить размер окна с повышенными привилегиями или окна, работающего от имени другого пользователя. - person Maxx Daymon; 17.12.2015
comment
@MaxxDaymon Здесь я подробно объяснил, почему это не работает в Windows 10: gist.github.com/tylerlong /7bdd18af120a6de3b471 Кажется, что это работает, но на самом деле это не так, потому что содержимое окна по-прежнему ограничено размером экрана. - person Tyler Long; 17.12.2015
comment
@TylerLong Я вижу, что размер окна WPF не изменяется, но размер других окон изменяется больше, чем рабочий стол в Windows 10. Например, я только что изменил размер экземпляра Firefox (показывающего Карты Google) до 6000x6000 и сделал снимок окна. В итоге я получил изображение карты размером 6000x6000 пикселей, обрамленное очень большим окном Firefox. Таким образом, может возникнуть проблема конкретно с WPF, но не с самой Windows 10. - person Maxx Daymon; 17.12.2015
comment
@MaxxDaymon согласился, то, что вы сказали, имеет смысл. Таким образом, этот метод работает для окон Windows 10, но для окон WPF. Мне удалось заставить его работать через WM_GETMINMAXINFO так как я создатель окна. - person Tyler Long; 18.12.2015
comment
Мне именно это было нужно в Xojo, чтобы преодолеть ограничение окна размеров экрана. Я пробовал SetWindowPos раньше, но SWP_NOSENDCHANGING действительно помог. Лучше всего, если Xojo впоследствии сообщит правильный размер окна. Спасибо :) - person Mitch Match; 14.09.2016
comment
Я пытаюсь использовать этот метод для создания скриншотов с высоким разрешением. Удалось ли вам сделать скриншоты окон, увеличенных с помощью этого метода? Я только что попробовал с блокнотом, и у меня получилось изображение размером 6000x6000, но часть блокнота, которая в данный момент не видна, просто черная - person codeling; 29.01.2018

Этот код на С# делает то, что вы просите. Окно намного шире рабочего стола.

 protected override void WndProc(ref Message m) {
        if (m.ToString().Contains("GETMINMAXINFO")) {
            //Hent data
            MINMAXINFO obj = (MINMAXINFO)Marshal.PtrToStructure(m.LParam, typeof(MINMAXINFO));
            //Endre
            if (obj.ptMaxSize.X > 0) {
                obj.ptMaxSize.X = 60000;
                obj.ptMaxSize.Y = 60000;
                obj.ptMaxTrackSize.X = 60000;
                obj.ptMaxTrackSize.Y = 60000;
                //Oppdater
                Marshal.StructureToPtr(obj, m.LParam, true);
            }
        }
        if (m.ToString().Contains("WINDOWPOSCHANGING")) {
            //Hent data
            WINDOWPOS obj = (WINDOWPOS)Marshal.PtrToStructure(m.LParam, typeof(WINDOWPOS));
            //Endre
            if (obj.cx > 0) {
                obj.cx = 8000;
                //Oppdater
                Marshal.StructureToPtr(obj, m.LParam, true);
            }
        }
        //Debug.WriteLine(m.ToString());
        base.WndProc(ref m);
    }











    [StructLayout(LayoutKind.Sequential)]
    internal struct WINDOWPOS {
        internal IntPtr hwnd;
        internal IntPtr hWndInsertAfter;
        internal int x;
        internal int y;
        internal int cx;
        internal int cy;
        internal uint flags;
    }

    [StructLayout(LayoutKind.Sequential)]
    internal struct MINMAXINFO {
        internal POINT ptReserverd;
        internal POINT ptMaxSize;
        internal POINT ptMaxPosition;
        internal POINT ptMinTrackSize;
        internal POINT ptMaxTrackSize;
    }
    [StructLayout(LayoutKind.Sequential)]
    internal struct POINT {
        internal int X;
        internal int Y;
    }
person Wolf5    schedule 25.01.2011
comment
Он сказал: «Я пытаюсь сделать эффект панорамирования на ноутбуке, чтобы у меня было больше места для работы». У старого ноутбука с меньшим размером ЖК-дисплея была такая функция. что подразумевает, что он хочет изменить размер окна, для которого он не пишет код. - person Maxx Daymon; 26.04.2013
comment
Путь более продвинутый, но должен быть выполним с небольшой инъекцией кода...? - person Wolf5; 29.04.2013
comment
Каждая программа будет отличаться. Внедрение в Python, .net и C++ будет отличаться. Ответ, который я изложил ниже, в сочетании с установкой глобального хука окна снимет ограничение на размер окна в целом, независимо от исполняемой цели. - person Maxx Daymon; 01.06.2013
comment
-1 за то, что не было приведено ни одного примера использования и кода для base.WndProc(ref m);. Без этого я чувствую, что ответ бесполезен - person Arsen Zahray; 06.06.2013

Вы можете сделать что-то вроде следующего кода в WinProc();

case WM_GETMINMAXINFO:
    {
        LPMINMAXINFO lpmmi = (LPMINMAXINFO)lParam; 
        GetWindowRect(GetDesktopWindow(), &actualDesktop);
        lpmmi->ptMaxTrackSize.x = 3000;// set the value that you really need.
        lpmmi->ptMaxTrackSize.y = 3000;// set the value that you really need.
    }
    break;

Приложение может использовать это сообщение, чтобы переопределить максимальный размер и положение окна по умолчанию или его минимальный или максимальный размер отслеживания по умолчанию.

person user6170414    schedule 07.04.2016

Если у вас есть видеокарта с возможностью подключения более одного экрана, другой обходной путь — настроить систему так, как если бы она использовала два экрана рядом друг с другом. Затем вы можете изменить размер окон до размера двух экранов вместе.

person Rafelb    schedule 28.12.2009

Размер окна, по-видимому, зависит от размера рабочего стола, а не от разрешения экрана; однако рабочий стол соответствует разрешению. Хитрость может заключаться в том, чтобы изменить размер рабочего стола или начать с него.

Некоторое время назад разработчик по имени Роберт Бреснер (его веб-сайт) создал продукт под названием sDesk (можно скачать отсюда), который расширил Windows за пределы разрешения экрана.

Что такое SDesk? SDesk не является многозадачной программой. Это программа, которая создает единый гигантский рабочий стол, выходящий за пределы видимой области монитора. В каждый момент времени видна только часть SDesk, как определено настройками рабочего стола Windows.

исходная домашняя страница программного обеспечения SDesk заархивирована здесь В Интернете нет текущей страницы (которую я смог найти), но доступ к этой архивной версии осуществляется через Way Back Machine, который кэширует большую часть Интернета.

Продукт SDesk является бесплатным. Однако исходный код не был включен. Вы можете посетить его контактную страницу (также доступна в архивной версии), чтобы узнать, доступен ли источник или может ли он быть приобретен для вашего исследования.

person John K    schedule 05.01.2010
comment
Это довольно аккуратно, но я не нашел способа сделать окна на этом большом виртуальном рабочем столе такими же большими, как виртуальный рабочий стол. Они по-прежнему ограничены реальным размером рабочего стола. - person loop; 26.01.2013

Перечислены только рекомендуемые разрешения экрана. Для дополнительных настроек нажмите кнопку Advanced на вкладке Settings, нажмите кнопку Adapter tab, а затем нажмите кнопку List all Modes. Выберите желаемое разрешение, уровень цвета и частоту обновления.

Я только что сделал это, здесь вы можете найти ответ в последнем пункте.

http://www.microsoft.com/resources/documentation/windows/xp/all/proddocs/en-us/display_change_screen_resolution.mspx?mfr=true

person vasile    schedule 06.11.2011

хорошо, я пробовал использовать нажатия клавиш для перемещения, изменения размера окон. Но система автоматически переместит окна обратно в видимую область рабочего стола в моей XP. Я также пробовал API SetWindowPos, и ничего не помогает. Лучше всего будет написать видеодрайвер, но это может потребовать дополнительного изучения. Рабочий стол 360 утверждает, что вы можете расширить рабочий стол по горизонтали. Но на самом деле это просто панорамирование текущего рабочего стола в более широком виртуальном пространстве. Любые окна внутри по-прежнему имеют ограничение по размеру, не превышающее разрешение вашего экрана.

Видеодрайвер устанавливал разрешение экрана (да, он должен быть совместим с возможностями экрана LCD/CRT), и Windows действительно ограничивала размер окна этим порогом. Я просто хочу работать с API пользовательского пространства.

person Community    schedule 16.01.2009

Мне нужно было вытолкнуть часть окна за верхнюю часть экрана, и я, наконец, смог сделать это с помощью этого скрипта AutoHotKey:

SetTitleMatchMode, 2
WinTitle := "Visual Studio Code"

; --- WinMove version

; WinMove, %WinTitle%, , 0, -64, 1280, 1504

; -- DLL version

WinGet, id, , %WinTitle%
Result := DllCall("SetWindowPos", "uint", id, "uint", HWND_TOP, "Int", 0, "Int", -64, "Int", 1280, "Int", 1504, "UInt", 0x400)

(Я хотел максимизировать область редактора VSCode, полностью скрыв строку заголовка и раздел вкладок, которые нельзя настроить в самой программе.)

person Isti115    schedule 12.11.2018

Для конкретного случая, когда требуется более удобное для экрана представление MSDN или любого другого сайта (например, StackOverflow), который плохо использует пространство экрана, я бы предложил применить к странице пользовательскую таблицу стилей, используя такой инструмент, как IE7Pro (IE), Greasemonkey (Firefox), Stylish (Fireox) или встроенный инструмент выбора таблиц стилей в Opera.

person Sparr    schedule 15.01.2009