Как захватить выбранный экран другого приложения с помощью java?

Мы пытаемся разработать утилиту для захвата экрана.

Как захватить выбранный экран другого приложения с помощью Java? И как мы добавляем выноску на захваченный экран?

Ответ 1

На основе Prajakta описание проекта, я считаю, что некоторое объяснение манипулирования снимком экрана в порядке (я думаю, что Джон отлично справился с объяснением как захватить снимок экрана, используя класс java.awt.Robot). Помните, как сказал Стив Маклеод, Java, возможно, не сможет автоматически определить местоположение окна, которое вы хотите захватить на экране. Это важно, потому что класс Robot должен знать это местоположение, автоматически или вручную от вас.

Выноски, текст, изображения и т.д. могут быть добавлены к снимку экрана через объект Graphics2D, который вы получаете, когда вы вызываете метод createGraphics() экрана. BufferedImage. Я настоятельно рекомендую вам проверить API Graphics2D, чтобы лучше понять, на что он способен. Я также рекомендую найти некоторые учебники, возможно, начиная с 2D-графического пособия с Sun. Книга, озаглавленная " Filthy Rich Клиенты, также может оказаться полезной.

Когда вы, наконец, захотите сохранить этот измененный снимок экрана, вы можете использовать один из методов "записи" ImageIO класс.

Вот очень простой пример от начала до конца. Это зависит от вас, чтобы заполнить все необходимые детали.

Надеюсь, это поможет немного!

Robot robot = new Robot();

// The hard part is knowing WHERE to capture the screen shot from
BufferedImage screenShot = robot.createScreenCapture(x, y, width, height);
Graphics2D graphics = screenShot.createGraphics();

// Add a label to the screen shot
Color textColor = Color.RED;
graphics.setColor(textColor);
graphics.drawString("Some text", textX, textY);

// Save your screen shot with its label
ImageIO.save(screenShot, "png", new File("myScreenShot.png"));

Ответ 2

Robot r = new Robot();
Toolkit t = Toolkit.getDefaultToolkit();
Dimension d = t.getScreenSize();
Image i = r.createScreenCapture( 0, 0, d.width, d.height );

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

Ответ 3

Возможно, класс java.awt.Robot поможет с экранами экрана, хотя я не думаю, что он способен находить отдельные окна, Что касается этих "выходов", класс Robot также может вызывать щелчки мыши и нажатия клавиш, если это то, что вы имеете в виду.

Ответ 4

Вероятно, вы можете обойти Robot, не имея возможности узнать границы окна, разрешив пользователю выбрать область, которую он хочет снять с экрана.

У вас есть два подхода, если опция полноэкранная, вам не нужно беспокоиться, следуйте описанному выше методу Robot.

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

  • Запустите нужное приложение.

  • Возьмите полный экран рабочего стола.

  • Создайте полноэкранное приложение, используя скриншот в качестве фона, ТОЛЬКО, чтобы пользователь мог выбрать область для захвата изображения (вы начинаете с маленького квадрата и позволяете пользователю перетаскивать, пока он не создаст нужный экран захват)

  • Передайте эту информацию роботу и сделайте скриншоты из этой области.

Что-то вроде этого:

alt text http://img136.imageshack.us/img136/8622/screencapturebb3.png

Если вам не нравится использовать полный скриншот в качестве фона, вы можете использовать прозрачное окно .

И сделайте то же самое: -)

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

Есть третий вариант, но секрет.

Ответ 5

Вам понадобится предоставить более конкретную информацию, чтобы получить значимую помощь. Для начала, в каких операционных системах это необходимо для работы? Вам нужно захватить содержимое отдельных окон или буквально целых дисплеев (вы использовали двусмысленный термин "выбранный экран другого приложения" в вашем исходном сообщении). Что конкретно вы хотите видеть, когда вы добавляете выноску на захваченный экран?

Ответ 6

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

Ответ 8

С помощью этого кода я мог бы создавать экраны определенных окон в Windows10, не забывайте о зависимости.

Кредиты идут в: Windows: как получить список всех видимых окон?

<dependency>
    <groupId>net.java.dev.jna</groupId>
    <artifactId>jna</artifactId>
    <version>4.5.0</version>
</dependency>

код:

import java.awt.AWTException;
import java.awt.Rectangle;
import java.awt.Robot;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;

import javax.imageio.ImageIO;

import com.sun.jna.Native;
import com.sun.jna.Structure;
import com.sun.jna.win32.StdCallLibrary;

public class Main {
    public static void main(String[] args) throws AWTException, IOException {

        int hWnd = User32.instance.FindWindowA(null, "Minesweeper X");
        WindowInfo w = getWindowInfo(hWnd);
        User32.instance.SetForegroundWindow(w.hwnd);
        BufferedImage createScreenCapture = new Robot().createScreenCapture(new Rectangle(w.rect.left, w.rect.top, w.rect.right - w.rect.left, w.rect.bottom - w.rect.top));
        ImageIO.write(createScreenCapture, "png", new File("screen.png"));

        // listAllWindows();
    }

    private static void listAllWindows() throws AWTException, IOException {
        final List<WindowInfo> inflList = new ArrayList<WindowInfo>();
        final List<Integer> order = new ArrayList<Integer>();
        int top = User32.instance.GetTopWindow(0);
        while (top != 0) {
            order.add(top);
            top = User32.instance.GetWindow(top, User32.GW_HWNDNEXT);
        }

        User32.instance.EnumWindows(new WndEnumProc() {
            public boolean callback(int hWnd, int lParam) {
                WindowInfo info = getWindowInfo(hWnd);
                inflList.add(info);
                return true;
            }

        }, 0);
        Collections.sort(inflList, new Comparator<WindowInfo>() {
            public int compare(WindowInfo o1, WindowInfo o2) {
                return order.indexOf(o1.hwnd) - order.indexOf(o2.hwnd);
            }
        });
        for (WindowInfo w : inflList) {
            System.out.println(w);
        }
    }

    public static  WindowInfo getWindowInfo(int hWnd) {
        RECT r = new RECT();
        User32.instance.GetWindowRect(hWnd, r);
        byte[] buffer = new byte[1024];
        User32.instance.GetWindowTextA(hWnd, buffer, buffer.length);
        String title = Native.toString(buffer);
        WindowInfo info = new WindowInfo(hWnd, r, title);
        return info;
    }

    public static interface WndEnumProc extends StdCallLibrary.StdCallCallback {
        boolean callback(int hWnd, int lParam);
    }

    public static interface User32 extends StdCallLibrary {
        public static final String SHELL_TRAY_WND = "Shell_TrayWnd";
        public static final int WM_COMMAND = 0x111;
        public static final int MIN_ALL = 0x1a3;
        public static final int MIN_ALL_UNDO = 0x1a0;

        final User32 instance = (User32) Native.loadLibrary("user32", User32.class);

        boolean EnumWindows(WndEnumProc wndenumproc, int lParam);

        boolean IsWindowVisible(int hWnd);

        int GetWindowRect(int hWnd, RECT r);

        void GetWindowTextA(int hWnd, byte[] buffer, int buflen);

        int GetTopWindow(int hWnd);

        int GetWindow(int hWnd, int flag);

        boolean ShowWindow(int hWnd);

        boolean BringWindowToTop(int hWnd);

        int GetActiveWindow();

        boolean SetForegroundWindow(int hWnd);

        int FindWindowA(String winClass, String title);

        long SendMessageA(int hWnd, int msg, int num1, int num2);

        final int GW_HWNDNEXT = 2;
    }

    public static class RECT extends Structure {
        public int left, top, right, bottom;

        @Override
        protected List<String> getFieldOrder() {
            List<String> order = new ArrayList<>();
            order.add("left");
            order.add("top");
            order.add("right");
            order.add("bottom");
            return order;
        }
    }

    public static class WindowInfo {
        int hwnd;
        RECT rect;
        String title;

        public WindowInfo(int hwnd, RECT rect, String title) {
            this.hwnd = hwnd;
            this.rect = rect;
            this.title = title;
        }

        public String toString() {
            return String.format("(%d,%d)-(%d,%d) : \"%s\"", rect.left, rect.top, rect.right, rect.bottom, title);
        }
    }
}