Отрисовка всех окон на нескольких мониторах - PullRequest
4 голосов
/ 30 марта 2009

Я использую следующий код для рисования на одном мониторе:

Point cursorLocation;
NativeMethods.GetCursorPos(out cursorLocation);
Screen screen = Screen.FromPoint(cursorLocation);

Point h1 = new Point(screen.Bounds.Left, cursorLocation.Y);
Point h2 = new Point(screen.Bounds.Right, cursorLocation.Y);
Point v1 = new Point(cursorLocation.X, screen.Bounds.Top);
Point v2 = new Point(cursorLocation.X, screen.Bounds.Bottom);

using (Graphics graphics = Graphics.FromHwnd(NativeMethods.GetDesktopWindow())) {
    NativeMethods.SHChangeNotify(0x8000000, 0x1000, IntPtr.Zero, IntPtr.Zero);
    graphics.DrawLine(Pens.Red, h1, h2);
    graphics.DrawLine(Pens.Red, v1, v2);
}

Собственно, должен теоретически рисовать на любом мониторе. Тем не менее, он опирается только на основной. Итак, чтобы исправить это, я получаю DC всех дисплеев и пытаюсь сделать это таким образом.

IntPtr hdc = NativeMethods.CreateDC("DISPLAY", IntPtr.Zero, IntPtr.Zero, IntPtr.Zero);
Graphics graphics = Graphics.FromHdc(hdc);
graphics.DrawLine(Pens.Red, h1, h2);
graphics.DrawLine(Pens.Red, v1, v2);
graphics.Dispose();
NativeMethods.ReleaseDC(IntPtr.Zero, hdc);

Иди к черту, это даже не рисует на экране вообще. Я пробовал различные перегрузки для CreateDC, а также искал SO и другие ресурсы, и я в тупике.


Как только это будет решено, кто-нибудь знает, как избавиться от мерцания, обновляя рабочий стол с помощью SHCHangeNotify? Я рисую только две линии, и она мерцает, как сумасшедшая ..)

Ответы [ 4 ]

3 голосов
/ 30 марта 2009

Это не ответ на ваш вопрос, но если у вас нет проблем с ним, я бы рекомендовал попробовать использовать WPF для решения этой проблемы. Я играл с другими типами взаимодействия с рабочим столом, такими как прозрачность, и WPF молниеносен по сравнению с альтернативой GDI.

Вы размещаете свое приложение wpf и изменяете его размер, чтобы он соответствовал всей области, на которой вы хотите рисовать. Затем установите его на прозрачный, и убедитесь, что его клик (я думаю, это по умолчанию на 100% прозрачности). Таким образом, до тех пор, пока у вас ничего не будет на этом большом холсте / форме WPF, все события мыши будут переходить на рабочий стол.

Тогда просто начните рисовать на нем. (Мне понравилось, потому что было очень легко добавлять эффекты к линиям и изображениям). Гарантированное отсутствие мерцания.

В качестве альтернативы вы можете использовать ту же схему на обычных Windows Forms.

Таким образом, вам не придется обращаться к GDI, чтобы выполнять свою работу.

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

1 голос
/ 30 марта 2013

это сработало для меня. я использовал EnumDisplayDevices для получения имен.

[DllImport("gdi32.dll")]
public static extern IntPtr CreateDC(string lpszDriver, string lpszDevice, string lpszOutput, IntPtr lpInitData);

var hdc = CreateDC(@"\\.\DISPLAY1", "", "", IntPtr.Zero);
Graphics g = Graphics.FromHdc(hdc);
var pt = Cursor.Position;
g.DrawEllipse(Pens.BlueViolet, pt.X - 100, pt.Y - 100, 200, 200);

подробнее здесь: http://msdn.microsoft.com/en-us/library/windows/desktop/dd145179(v=vs.85).aspx

1 голос
/ 31 марта 2009

К сожалению, ни один из ответов не поможет по следующим причинам:

Я ограничен Windows Forms, так как это базовая структура, созданная для WF. Я попробовал трюк с TransparencyKey / Form, он все еще слишком сильно мигает.

Я серьезно попробовал почти десять различных методов, и даже мои результаты поиска в Google для DirectX / Direct3D, C # Desktop Hooks и других приводили меня к безрезультатности.

Все, что я пытаюсь сделать, это нарисовать перекрестие, охватывающее весь рабочий стол, 1px x 1px .. наверняка у кого-то должен быть какой-то пример того, как это сделать без мерцания и хорошей производительности :? D3D, DX, GDI или как? : \

0 голосов
/ 30 марта 2009

Не могу помочь по первой части. Я предполагаю, что вы рисуете линии в событии Paint. Используйте двойную буферизацию, чтобы избавиться от мерцания.

...