작업표시줄 제목으로 윈도우 찾고 포커스하기 (FindWindow, SetForegroundWindow)

작업표시줄 제목으로 윈도우 찾고 포커스하기 (FindWindow, SetForegroundWindow)

기존의 방식은 (1)클래스 네임 또는 (2)제목표시줄로 윈도우 핸들을 얻고(FindWindow), 포커스를 하는(SetForegroundWindow) 방식이었다.

package com;

import java.awt.Robot;

import com.sun.jna.platform.win32.User32;
import com.sun.jna.platform.win32.WinDef;

public class MainClass {

 public static void main(String[] args) {
  
  WinDef.HWND hWnd;//윈도우 핸들
  try{
     //로봇 선언
   Robot robot=new Robot();
 
   //메모장이 켜졌는지 검사
   hWnd=null;
   while(hWnd==null){
    System.out.println(“메모장을 찾는 중입니다”);
    robot.delay(500);
    //hWnd = User32.INSTANCE.FindWindow(“Notepad”, null);
    hWnd = User32.INSTANCE.FindWindow(null, “제목 없음 – 메모장”);
   }
   User32.INSTANCE.SetForegroundWindow(hWnd);
  }catch(Exception ex){System.out.println();}
 }
}

하지만 위 소스의 단점은 “제목 없음 – 메모장” 이라고 작업표시줄 상의 풀 네임을 정확히 적어야 한다는 것이었다.

아래는 이를 개선한 소스이다. 현재 띄워진 모든 창들을 가져온 후, indexof 를 활용하여 핸들을 얻는다.

이렇게 하면 “제목 없음 – 메모장”이라는 풀 네임이 아니라 “제목”, “제목 없”. “제목 없음”.. 만으로도 핸들을 찾을 수 있다.

package com;

import java.awt.List;
import java.awt.Robot;
import java.util.ArrayList;

import com.sun.jna.Native;
import com.sun.jna.Pointer;
import com.sun.jna.platform.win32.*;
import com.sun.jna.platform.win32.Netapi32Util.User;
import com.sun.jna.platform.win32.WinDef.HDC;
import com.sun.jna.platform.win32.WinDef.HWND;
import com.sun.jna.platform.win32.WinDef.RECT;
import com.sun.jna.platform.win32.WinUser.WNDENUMPROC;

public class MainClass {

 public static void main(String[] args) {
  MainClass m=new MainClass();
  User32.INSTANCE.SetForegroundWindow(m.getHwndByName(“제목 없음”));
 }
 
 private String str=””;
 private HWND res=null;
 
 public String getStr() {
  return str;
 }
 public void setStr(String str) {
  this.str = str;
 }
 public HWND getRes() {
  return res;
 }
 public void setRes(HWND res) {
  this.res = res;
 }

 public HWND getHwndByName(String str){
  HWND res=null;
  setStr(str);
  
  try{
   User32.INSTANCE.EnumWindows(new WNDENUMPROC() {
             int count = 0;
             String str=””;
            
             public boolean callback(HWND hWnd, Pointer arg1) {
                 char[] windowText = new char[512];
                 User32.INSTANCE.GetWindowText(hWnd, windowText, 512);
                 String wText = Native.toString(windowText);
                 RECT rectangle = new RECT();
                 User32.INSTANCE.GetWindowRect(hWnd, rectangle);
                 // get rid of this if block if you want all windows regardless
                 // of whether
                 // or not they have text
                 // second condition is for visible and non minimised windows
                 if (wText.isEmpty() || !(User32.INSTANCE.IsWindowVisible(hWnd)
                         && rectangle.left > -32000)) {
                     return true;
                 }
                
                 //핸들의 클래스 네임 얻기
                 char[] c=new char[512];
                 User32.INSTANCE.GetClassName(hWnd, c, 512);
                 String clsName=String.valueOf(c).trim();

                 if(wText.indexOf(getStr())>=0){
                  //원하는 글자가 포함되어 있다면 핸들값을 set함
                  setRes(hWnd);
                  
                  System.out.println(
                          “hwnd:”+hWnd+”,”+
                          “번호:” + (++count) + “,텍스트:” + wText+”,”+
                          “위치:(“+rectangle.left+”,”+rectangle.top+”)~(“+rectangle.right+”,”+rectangle.bottom+”),”+
                          “클래스네임:”+clsName);

                 }
                 return true;
             }
         }, null);
   
  }catch(Exception ex){System.out.println(ex.getMessage());}
  
  return getRes();
  
 }

}