원격 제어 메커니즘이 애플리케이션에서 무언가를 활성화 할 때 포 그라운드로 가져와야하는 Java 애플리케이션이 있습니다.
이를 얻기 위해, 우리는 애플리케이션의 프레임 (확장자 JFrame
) 을 나타내는 클래스의 호출 된 메서드에서 다음 구현을 깨달았습니다 .
setVisible(true);
toFront();
Windows XP에서는 처음 호출 될 때 작동하고 두 번째로 작업 표시 줄의 탭만 깜박이고 프레임이 더 이상 앞으로 나오지 않습니다. Win2k도 마찬가지입니다. Vista에서는 잘 작동하는 것 같습니다.
아이디어가 있습니까?
답변
가능한 해결책은 다음과 같습니다.
java.awt.EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
myFrame.toFront();
myFrame.repaint();
}
});
답변
JFrame
Ubuntu (Java 1.6.0_10)에서 a 를 전면에 가져 오는 데 동일한 문제가 발생했습니다 . 문제를 해결할 수있는 유일한 방법은 WindowListener
. 특히, 호출 JFrame
될 때마다 항상 맨 위에 있도록 설정 toFront()
하고 windowDeactivated
이벤트 핸들러를 제공 해야했습니다.setAlwaysOnTop(false)
.
따라서 여기에 JFrame
모든 애플리케이션 프레임을 유도하는 데 사용되는 base에 배치 할 수있는 코드가 있습니다 .
@Override
public void setVisible(final boolean visible) {
// make sure that frame is marked as not disposed if it is asked to be visible
if (visible) {
setDisposed(false);
}
// let's handle visibility...
if (!visible || !isVisible()) { // have to check this condition simply because super.setVisible(true) invokes toFront if frame was already visible
super.setVisible(visible);
}
// ...and bring frame to the front.. in a strange and weird way
if (visible) {
toFront();
}
}
@Override
public void toFront() {
super.setVisible(true);
int state = super.getExtendedState();
state &= ~JFrame.ICONIFIED;
super.setExtendedState(state);
super.setAlwaysOnTop(true);
super.toFront();
super.requestFocus();
super.setAlwaysOnTop(false);
}
프레임을 표시하거나 전면 통화로 가져와야 할 때마다 frame.setVisible(true)
.
우분투 9.04로 옮긴 이후 로 볼 수 있듯이 WindowListener
호출을위한를 가질 필요가없는 것 같습니다 super.setAlwaysOnTop(false)
. 이 코드는 메서드로 이동 toFront()
되었으며setVisible()
.
메서드 setVisible()
는 항상 EDT에서 호출되어야합니다.
답변
Windows에는 창이 초점을 훔치는 것을 방지하는 기능이 있습니다. 대신 작업 표시 줄 아이콘이 깜박입니다. XP에서는 기본적으로 켜져 있습니다 (제가 변경 한 유일한 곳은 TweakUI를 사용하는 것이지만 어딘가에 레지스트리 설정이 있습니다). Vista에서는 기본 UI를 사용하여 기본값을 변경하거나 사용자가 액세스 할 수있는 설정으로 노출했을 수 있습니다.
윈도우 2K 이후로 윈도우가 강제로 앞쪽으로 향하는 것을 방지하고 초점을 맞추는 기능은 Windows 2K 이후의 기능입니다.
즉, 작업하는 동안 내 활동을 기록하도록 상기시키는 데 사용하는 작은 Java 앱이 있으며 30 분마다 활성 창 (물론 구성 가능)이됩니다. Windows XP에서 항상 일관되게 작동하며 제목 표시 줄 창을 깜박이지 않습니다. 타이머 이벤트 발생의 결과로 UI 스레드에서 호출되는 다음 코드를 사용합니다.
if(getState()!=Frame.NORMAL) { setState(Frame.NORMAL); }
toFront();
repaint();
(최소화하면 첫 번째 줄이 복원됩니다 … 실제로 최대화하면 복원되지만 결코 그렇지 않습니다).
일반적으로이 앱은 최소화되어 있지만 텍스트 편집기 뒤에있는 경우가 많습니다. 그리고 제가 말했듯이 항상 작동합니다.
나는 당신의 문제가 무엇인지에 대한 아이디어를 가지고 있습니다-아마도 당신은 setVisible () 호출과 경쟁 조건이 있습니다. 창이 호출 될 때 실제로 표시되지 않는 한 toFront ()는 유효하지 않을 수 있습니다. 이전에 requestFocus () 에이 문제가 발생했습니다. 창 활성화 이벤트의 UI 리스너에 toFront () 호출을 넣어야 할 수도 있습니다.
2014-09-07 : 어느 시점에서 위의 코드가 Java 6 또는 7에서 작동을 멈췄습니다. 조사와 실험을 한 후 코드를 업데이트하여 창의 toFront
메서드 를 재정의 해야했습니다 (수정 된 코드와 함께 위) :
setVisible(true);
toFront();
requestFocus();
repaint();
...
public @Override void toFront() {
int sta = super.getExtendedState() & ~JFrame.ICONIFIED & JFrame.NORMAL;
super.setExtendedState(sta);
super.setAlwaysOnTop(true);
super.toFront();
super.requestFocus();
super.setAlwaysOnTop(false);
}
Java 8_20부터이 코드는 제대로 작동하는 것 같습니다.
답변
다음은 실제로 작동하는 방법입니다 (Windows Vista에서 테스트 됨) .D
frame.setExtendedState(JFrame.ICONIFIED);
frame.setExtendedState(fullscreen ? JFrame.MAXIMIZED_BOTH : JFrame.NORMAL);
fullscreen 변수는 앱을 전체 화면으로 실행할 것인지 창으로 실행할 것인지를 나타냅니다.
이것은 작업 표시 줄을 깜박이지 않지만 창을 안정적으로 앞으로 가져옵니다.
답변
Hj, Fedora KDE 14에서는 모든 방법이 작동하지 않습니다. Oracle이이 문제를 해결하기를 기다리는 동안 창을 앞으로 가져올 수있는 더러운 방법이 있습니다.
import java.awt.MouseInfo;
import java.awt.Point;
import java.awt.Robot;
import java.awt.event.InputEvent;
public class FrameMain extends javax.swing.JFrame {
//...
private final javax.swing.JFrame mainFrame = this;
private void toggleVisible() {
setVisible(!isVisible());
if (isVisible()) {
toFront();
requestFocus();
setAlwaysOnTop(true);
try {
//remember the last location of mouse
final Point oldMouseLocation = MouseInfo.getPointerInfo().getLocation();
//simulate a mouse click on title bar of window
Robot robot = new Robot();
robot.mouseMove(mainFrame.getX() + 100, mainFrame.getY() + 5);
robot.mousePress(InputEvent.BUTTON1_DOWN_MASK);
robot.mouseRelease(InputEvent.BUTTON1_DOWN_MASK);
//move mouse to old location
robot.mouseMove((int) oldMouseLocation.getX(), (int) oldMouseLocation.getY());
} catch (Exception ex) {
//just ignore exception, or you can handle it as you want
} finally {
setAlwaysOnTop(false);
}
}
}
//...
}
그리고 이것은 내 Fedora KDE 14에서 완벽하게 작동합니다. 🙂
답변
이 간단한 방법은 Windows 7에서 완벽하게 작동했습니다.
private void BringToFront() {
java.awt.EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
if(jFrame != null) {
jFrame.toFront();
jFrame.repaint();
}
}
});
}
답변
나는 당신의 대답을 테스트했고 Stefan Reich의 대답 만이 나를 위해 일했습니다. 창을 이전 상태 (최대화 / 정상)로 복원 할 수는 없었지만. 이 돌연변이가 더 잘 발견되었습니다.
view.setState(java.awt.Frame.ICONIFIED);
view.setState(java.awt.Frame.NORMAL);
즉 setState
대신 setExtendedState
.
