
com.googlecode.lanterna.gui.Window Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of lanterna Show documentation
Show all versions of lanterna Show documentation
Java library for creating text-based terminal GUIs
/*
* This file is part of lanterna (http://code.google.com/p/lanterna/).
*
* lanterna is free software: you can redistribute it and/or modify
* it under the terms of the GNU Lesser General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public License
* along with this program. If not, see .
*
* Copyright (C) 2010-2014 Martin
*/
package com.googlecode.lanterna.gui;
import java.util.ArrayList;
import java.util.List;
import com.googlecode.lanterna.gui.Theme.Category;
import com.googlecode.lanterna.gui.component.EmptySpace;
import com.googlecode.lanterna.gui.component.Panel;
import com.googlecode.lanterna.gui.layout.LayoutParameter;
import com.googlecode.lanterna.gui.listener.ComponentAdapter;
import com.googlecode.lanterna.gui.listener.ContainerListener;
import com.googlecode.lanterna.gui.listener.WindowListener;
import com.googlecode.lanterna.input.KeyStroke;
import com.googlecode.lanterna.TerminalPosition;
import com.googlecode.lanterna.TerminalSize;
import java.io.IOException;
/**
* The Window class is the basis for Lanternas GUI system. The workflow is to
* create and show modal windows and promt the user for input. A window, once
* displayed, will take over control by entering an event loop and won't come
* back until the window is closed.
* @author Martin
*/
@SuppressWarnings({"SameParameterValue", "WeakerAccess"})
@Deprecated
public class Window
{
private final List windowListeners;
private final List invalidatorAlerts;
private GUIScreen owner;
private final WindowContentPane contentPane;
private Interactable currentlyInFocus;
private TerminalSize windowSizeOverride;
private boolean soloWindow;
private boolean drawShadow;
/**
* Creates a new window
* @param title Title for the new window
*/
public Window(String title)
{
this.windowListeners = new ArrayList();
this.invalidatorAlerts = new ArrayList();
this.owner = null;
this.contentPane = new WindowContentPane(title);
this.currentlyInFocus = null;
this.soloWindow = false;
this.windowSizeOverride = null;
this.drawShadow = true;
}
public void addWindowListener(WindowListener listener)
{
windowListeners.add(listener);
}
/**
* @return The GUIScreen which this window is displayed on
*/
public GUIScreen getOwner()
{
return owner;
}
void setOwner(GUIScreen owner)
{
this.owner = owner;
}
/**
* @return The border of this window
*/
public Border getBorder()
{
return contentPane.getBorder();
}
public void setBorder(Border border)
{
if(border != null)
contentPane.setBorder(border);
}
/**
* Returns the current window size override or {@code null} if none is set
* @return Override for the window size or {@code null}
*/
public TerminalSize getWindowSizeOverride() {
return windowSizeOverride;
}
/**
* Sets the size of the window to a fixed value, rather than using automatic size calculation.
* If you call this method with {@code windowSizeOverride} parameter set to {@code null}, the
* automatic size calculation will be activated again.
* @param windowSizeOverride Size the window should have, or {@code null} if you want to use
* automatic size calculation
*/
public void setWindowSizeOverride(TerminalSize windowSizeOverride) {
this.windowSizeOverride = windowSizeOverride;
}
/**
* @return How big this window would like to be
*/
TerminalSize getPreferredSize()
{
TerminalSize override = getWindowSizeOverride();
if(override != null)
return override;
else
return contentPane.getPreferredSize(); //Automatically calculate the size
}
void repaint(TextGraphics graphics)
{
graphics.applyTheme(graphics.getTheme().getDefinition(Category.DIALOG_AREA));
graphics.fillRectangle(' ', new TerminalPosition(0, 0), new TerminalSize(graphics.getWidth(), graphics.getHeight()));
contentPane.repaint(graphics);
}
private void invalidate()
{
for(WindowListener listener: windowListeners)
listener.onWindowInvalidated(this);
}
/**
* Don't use the method, call {@code addComponent(new EmptySpace(1, 1))} instead
* @deprecated
*/
@Deprecated
public void addEmptyLine()
{
addComponent(new EmptySpace(1, 1));
}
public void addComponent(Component component, LayoutParameter... layoutParameters)
{
if(component == null)
return;
contentPane.addComponent(component, layoutParameters);
ComponentInvalidatorAlert invalidatorAlert = new ComponentInvalidatorAlert(component);
invalidatorAlerts.add(invalidatorAlert);
component.addComponentListener(invalidatorAlert);
checkFocus();
invalidate();
}
/**
* This method will, if nothing is in focus, scan through all components
* again and find something to focus on.
*/
void checkFocus()
{
if(currentlyInFocus == null) {
setFocus(contentPane.nextFocus(null));
invalidate();
}
}
public void addContainerListener(ContainerListener cl)
{
contentPane.addContainerListener(cl);
}
public void removeContainerListener(ContainerListener cl)
{
contentPane.removeContainerListener(cl);
}
public Component getComponentAt(int index)
{
return contentPane.getComponentAt(index);
}
/**
* @return How many top-level components this window has
*/
public int getComponentCount()
{
return contentPane.getComponentCount();
}
/**
* Removes a top-level component from the window
* @param component Top-level component to remove
*/
public void removeComponent(Component component)
{
if(component instanceof InteractableContainer) {
InteractableContainer container = (InteractableContainer)component;
if(container.hasInteractable(currentlyInFocus)) {
Interactable original = currentlyInFocus;
Interactable current = contentPane.nextFocus(original);
while(container.hasInteractable(current) && original != current)
current = contentPane.nextFocus(current);
if(container.hasInteractable(current))
setFocus(null);
else
setFocus(current);
}
}
else if(component == currentlyInFocus)
setFocus(contentPane.nextFocus(currentlyInFocus));
contentPane.removeComponent(component);
for(ComponentInvalidatorAlert invalidatorAlert: invalidatorAlerts) {
if(component == invalidatorAlert.component) {
component.removeComponentListener(invalidatorAlert);
invalidatorAlerts.remove(invalidatorAlert);
break;
}
}
}
/**
* Removes all components from the window
*/
public void removeAllComponents()
{
while(getComponentCount() > 0)
removeComponent(getComponentAt(0));
}
TerminalPosition getWindowHotspotPosition()
{
if(currentlyInFocus == null)
return null;
else
return currentlyInFocus.getHotspot();
}
public void onKeyPressed(KeyStroke key) throws IOException
{
if(currentlyInFocus != null) {
Interactable.Result result = currentlyInFocus.keyboardInteraction(key);
if(result.isNextInteractable()) {
Interactable nextItem = contentPane.nextFocus(currentlyInFocus);
if(nextItem == null)
nextItem = contentPane.nextFocus(null);
setFocus(nextItem, result.asFocusChangeDirection());
}
else if(result.isPreviousInteractable()) {
Interactable prevItem = contentPane.previousFocus(currentlyInFocus);
if(prevItem == null)
prevItem = contentPane.previousFocus(null);
setFocus(prevItem, result.asFocusChangeDirection());
}
else if(result == Interactable.Result.EVENT_NOT_HANDLED) {
//Try to find a shortcut
if(currentlyInFocus instanceof Component) {
Container parentContainer = ((Component)currentlyInFocus).getParent();
while(parentContainer != null) {
if(parentContainer instanceof InteractableContainer) {
//If we could fire off a shortcut, stop here
if(((InteractableContainer)parentContainer).triggerShortcut(key))
return;
}
//Otherwise try one level higher
parentContainer = parentContainer.getParent();
}
}
//There was no shortcut
onUnhandledKeyPress(key);
}
}
else {
onUnhandledKeyPress(key);
}
}
protected void onUnhandledKeyPress(KeyStroke key) {
for(WindowListener listener: windowListeners)
listener.onUnhandledKeyboardInteraction(this, key);
}
public boolean isSoloWindow()
{
return soloWindow;
}
/**
* If set to true, when this window is shown, all previous windows are
* hidden. Set to false to show them again.
*/
public void setSoloWindow(boolean soloWindow)
{
this.soloWindow = soloWindow;
}
public boolean isDrawShadow() {
return drawShadow;
}
public void setDrawShadow(boolean drawShadow) {
this.drawShadow = drawShadow;
}
protected boolean maximisesVertically()
{
return contentPane.maximisesVertically();
}
protected boolean maximisesHorisontally()
{
return contentPane.maximisesHorisontally();
}
public void setFocus(Interactable newFocus)
{
setFocus(newFocus, null);
}
protected void setFocus(Interactable newFocus, Interactable.FocusChangeDirection direction)
{
if(currentlyInFocus != null)
currentlyInFocus.onLeaveFocus(direction);
//Fire the focus changed event
for(WindowListener listener: windowListeners) {
listener.onFocusChanged(this, currentlyInFocus, newFocus);
}
currentlyInFocus = newFocus;
if(currentlyInFocus != null)
currentlyInFocus.onEnterFocus(direction);
invalidate();
}
protected Interactable getInputFocusedComponent() {
return currentlyInFocus;
}
public void close()
{
if(owner != null)
owner.closeWindow(this);
}
protected void onVisible()
{
for(WindowListener listener: windowListeners)
listener.onWindowShown(this);
}
protected void onClosed()
{
for(WindowListener listener: windowListeners)
listener.onWindowClosed(this);
}
@Override
public String toString() {
return contentPane.getTitle();
}
private class ComponentInvalidatorAlert extends ComponentAdapter
{
private final Component component;
public ComponentInvalidatorAlert(Component component)
{
this.component = component;
}
public Component getComponent()
{
return component;
}
@Override
public void onComponentInvalidated(Component component)
{
invalidate();
}
}
/**
* Private class to get through some method restrictions
*/
private class WindowContentPane extends Panel {
public WindowContentPane(String title) {
super(title);
}
@Override
public Window getWindow() {
return Window.this;
}
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy