Скриншот только видимого рабочего стола - PullRequest
0 голосов
/ 27 октября 2011

Я использую JNA / CGWindowListCreateImage , чтобы сделать снимок экрана в системе OS X.

Код в основном взят из этого вопроса:

Недопустимый доступ к памяти в Rococoa

Моя проблема в том, что, хотя он «работает», он принимает копию всего рабочего стола, размер которого изменяется в зависимости от положения других окон (например, если другое окно частично отображается на экране, то часть, которая является не на экране будет способствовать увеличению размера "рабочего стола".

Итак, на 1680x1050 я получаю «скриншот рабочего стола» (ну, не совсем), который может быть 1714x1084 пикселей и т. Д.

Я так понимаю, что, передав правильное происхождение / границы, моя проблема исчезнет, ​​но я не знаю, как получить эту информацию, особенно без использования JNA.

Вот в основном то, что у меня есть:

final int windowIdDesktop = 0;

QuartzLibrary.CGRect bounds = new QuartzLibrary.CGRect.CGRectByValue();
bounds.origin = new QuartzLibrary.CGPoint();
bounds.origin.x = 0;
bounds.origin.y = 0;
bounds.size = new QuartzLibrary.CGSize();
bounds.size.width = 0;
bounds.size.height = 0;
ID imageRef = QuartzLibrary.INSTANCE.CGWindowListCreateImage(bounds,QuartzLibrary.kCGWindowListOptionOnScreenOnly, windowIdDesktop, QuartzLibrary.kCGWindowImageDefault);

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

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

NSRect desktopRect = NSZeroRect; for (NSScreen *screen in [NSScreen screens]) { desktopRect = NSUnionRect(desktopRect, [screen frame]); }

Почему это необходимо и как я могу перевести это на JNA? Все, что мне нужно знать, это происхождение видимой части экрана (по крайней мере, я так думаю)

CGWindowListCreateImage сообщает следующее:

Setting
   `screenBounds' to `CGRectInfinite' will include all the windows on the
   entire desktop. Setting `screenBounds' to `CGRectNull' will use the
   bounding box of the specified windows as the screen space rectangle.

Но я действительно не знаю, как я могу "симулировать" или передать либо CGRectInfinite , либо CGRectNull в мой код JNA. Я даже не уверен, что это путь.

1 Ответ

0 голосов
/ 21 декабря 2011

Вы пытались просто использовать предоставленные Java методы для получения размера дисплея?Java обеспечивает следующее (для одного дисплея):

// Get the size of the default display
Dimension dim = Toolkit.getDefaultToolkit().getScreenSize();

Если доступно более одного дисплея, то будет получен размер каждого дисплея:

GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
GraphicsDevice[] gs = ge.getScreenDevices();

// Get size of each display
for (int i=0; i<gs.length; i++) {
    DisplayMode dm = gs[i].getDisplayMode();
    int screenWidth = dm.getWidth();
    int screenHeight = dm.getHeight();
}
...