mirror of
https://github.com/processing/processing4.git
synced 2026-02-11 17:40:48 +01:00
375 lines
8.5 KiB
Java
Executable File
375 lines
8.5 KiB
Java
Executable File
/*
|
|
Part of the XQMode project - https://github.com/Manindra29/XQMode
|
|
|
|
Under Google Summer of Code 2012 -
|
|
http://www.google-melange.com/gsoc/homepage/google/gsoc2012
|
|
|
|
Copyright (C) 2012 Manindra Moharana
|
|
|
|
This program is free software; you can redistribute it and/or modify
|
|
it under the terms of the GNU General Public License version 2
|
|
as published by the Free Software Foundation.
|
|
|
|
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 General Public License for more details.
|
|
|
|
You should have received a copy of the GNU General Public License
|
|
along with this program; if not, write to the Free Software Foundation,
|
|
Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
|
*/
|
|
|
|
package processing.mode.experimental;
|
|
|
|
import java.awt.BorderLayout;
|
|
import java.awt.Frame;
|
|
import java.awt.Point;
|
|
import java.awt.event.ComponentEvent;
|
|
import java.awt.event.ComponentListener;
|
|
import java.awt.event.WindowAdapter;
|
|
import java.awt.event.WindowEvent;
|
|
|
|
import javax.swing.JFrame;
|
|
import javax.swing.JPanel;
|
|
import javax.swing.JScrollPane;
|
|
import javax.swing.WindowConstants;
|
|
import javax.swing.border.EmptyBorder;
|
|
import javax.swing.table.TableModel;
|
|
|
|
import processing.app.Editor;
|
|
import processing.app.Toolkit;
|
|
|
|
/**
|
|
* Error Window that displays a tablular list of errors. Clicking on an error
|
|
* scrolls to its location in the code.
|
|
*
|
|
* @author Manindra Moharana <me@mkmoharana.com>
|
|
*
|
|
*/
|
|
public class ErrorWindow extends JFrame {
|
|
|
|
private JPanel contentPane;
|
|
/**
|
|
* The table displaying the errors
|
|
*/
|
|
protected XQErrorTable errorTable;
|
|
/**
|
|
* Scroll pane that contains the Error Table
|
|
*/
|
|
protected JScrollPane scrollPane;
|
|
|
|
protected DebugEditor thisEditor;
|
|
private JFrame thisErrorWindow;
|
|
|
|
/**
|
|
* Handles the sticky Problem window
|
|
*/
|
|
private DockTool2Base Docker;
|
|
|
|
protected ErrorCheckerService errorCheckerService;
|
|
|
|
/**
|
|
* Preps up ErrorWindow
|
|
*
|
|
* @param editor
|
|
* - Editor
|
|
* @param ecs - ErrorCheckerService
|
|
*/
|
|
public ErrorWindow(DebugEditor editor, ErrorCheckerService ecs) {
|
|
thisErrorWindow = this;
|
|
errorCheckerService = ecs;
|
|
thisEditor = editor;
|
|
setTitle("Problems");
|
|
prepareFrame();
|
|
}
|
|
|
|
/**
|
|
* Sets up ErrorWindow
|
|
*/
|
|
protected void prepareFrame() {
|
|
Toolkit.setIcon(this);
|
|
setDefaultCloseOperation(WindowConstants.HIDE_ON_CLOSE);
|
|
// Default size: setBounds(100, 100, 458, 160);
|
|
setBounds(100, 100, 458, 160); // Yeah, I hardcode such things sometimes. Hate me.
|
|
|
|
contentPane = new JPanel();
|
|
contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
|
|
setContentPane(contentPane);
|
|
contentPane.setLayout(new BorderLayout(0, 0));
|
|
|
|
scrollPane = new JScrollPane();
|
|
contentPane.add(scrollPane);
|
|
|
|
errorTable = new XQErrorTable(errorCheckerService);
|
|
scrollPane.setViewportView(errorTable);
|
|
|
|
try {
|
|
Docker = new DockTool2Base();
|
|
addListeners();
|
|
} catch (Exception e) {
|
|
System.out.println("addListeners() acted silly.");
|
|
e.printStackTrace();
|
|
}
|
|
|
|
if (thisEditor != null) {
|
|
setLocation(new Point(thisEditor.getLocation().x
|
|
+ thisEditor.getWidth(), thisEditor.getLocation().y));
|
|
}
|
|
|
|
}
|
|
|
|
/**
|
|
* Updates the error table with new data(Table Model). Called from Error
|
|
* Checker Service.
|
|
*
|
|
* @param tableModel
|
|
* - Table Model
|
|
* @return True - If error table was updated successfully.
|
|
*/
|
|
synchronized public boolean updateTable(final TableModel tableModel) {
|
|
// XQErrorTable handles evrything now
|
|
return errorTable.updateTable(tableModel);
|
|
}
|
|
|
|
/**
|
|
* Adds various listeners to components of EditorWindow and to the Editor
|
|
* window
|
|
*/
|
|
protected void addListeners() {
|
|
|
|
if (thisErrorWindow == null)
|
|
System.out.println("ERW null");
|
|
|
|
thisErrorWindow.addComponentListener(new ComponentListener() {
|
|
|
|
@Override
|
|
public void componentShown(ComponentEvent e) {
|
|
|
|
}
|
|
|
|
@Override
|
|
public void componentResized(ComponentEvent e) {
|
|
Docker.tryDocking();
|
|
}
|
|
|
|
@Override
|
|
public void componentMoved(ComponentEvent e) {
|
|
Docker.tryDocking();
|
|
}
|
|
|
|
@Override
|
|
public void componentHidden(ComponentEvent e) {
|
|
|
|
}
|
|
});
|
|
|
|
thisErrorWindow.addWindowListener(new WindowAdapter() {
|
|
|
|
@Override
|
|
public void windowClosing(WindowEvent e) {
|
|
thisEditor.problemWindowMenuCB.setSelected(false);
|
|
}
|
|
|
|
@Override
|
|
public void windowDeiconified(WindowEvent e) {
|
|
thisEditor.setExtendedState(Frame.NORMAL);
|
|
}
|
|
|
|
});
|
|
|
|
if (thisEditor == null) {
|
|
System.out.println("Editor null");
|
|
return;
|
|
}
|
|
|
|
thisEditor.addWindowListener(new WindowAdapter() {
|
|
|
|
@Override
|
|
public void windowClosing(WindowEvent e) {
|
|
|
|
}
|
|
|
|
@Override
|
|
public void windowClosed(WindowEvent e) {
|
|
errorCheckerService.pauseThread();
|
|
errorCheckerService.stopThread(); // Bye bye thread.
|
|
thisErrorWindow.dispose();
|
|
}
|
|
|
|
@Override
|
|
public void windowIconified(WindowEvent e) {
|
|
thisErrorWindow.setExtendedState(Frame.ICONIFIED);
|
|
}
|
|
|
|
@Override
|
|
public void windowDeiconified(WindowEvent e) {
|
|
thisErrorWindow.setExtendedState(Frame.NORMAL);
|
|
}
|
|
|
|
});
|
|
|
|
thisEditor.addComponentListener(new ComponentListener() {
|
|
|
|
@Override
|
|
public void componentShown(ComponentEvent e) {
|
|
|
|
}
|
|
|
|
@Override
|
|
public void componentResized(ComponentEvent e) {
|
|
if (Docker.isDocked()) {
|
|
Docker.dock();
|
|
} else {
|
|
Docker.tryDocking();
|
|
}
|
|
}
|
|
|
|
@Override
|
|
public void componentMoved(ComponentEvent e) {
|
|
|
|
if (Docker.isDocked()) {
|
|
Docker.dock();
|
|
} else {
|
|
Docker.tryDocking();
|
|
}
|
|
|
|
}
|
|
|
|
@Override
|
|
public void componentHidden(ComponentEvent e) {
|
|
// System.out.println("ed hidden");
|
|
}
|
|
});
|
|
|
|
}
|
|
|
|
|
|
/**
|
|
* Implements the docking feature of the tool - The frame sticks to the
|
|
* editor and once docked, moves along with it as the editor is resized,
|
|
* moved, or closed.
|
|
*
|
|
* This class has been borrowed from Tab Manager tool by Thomas Diewald. It
|
|
* has been slightly modified and used here.
|
|
*
|
|
* @author Thomas Diewald , http://thomasdiewald.com
|
|
*/
|
|
private class DockTool2Base {
|
|
|
|
private int docking_border = 0;
|
|
private int dock_on_editor_y_offset_ = 0;
|
|
private int dock_on_editor_x_offset_ = 0;
|
|
|
|
// ///////////////////////////////
|
|
// ____2____
|
|
// | |
|
|
// | |
|
|
// 0 | editor | 1
|
|
// | |
|
|
// |_________|
|
|
// 3
|
|
// ///////////////////////////////
|
|
|
|
// public void reset() {
|
|
// dock_on_editor_y_offset_ = 0;
|
|
// dock_on_editor_x_offset_ = 0;
|
|
// docking_border = 0;
|
|
// }
|
|
|
|
public boolean isDocked() {
|
|
return (docking_border >= 0);
|
|
}
|
|
|
|
private final int MAX_GAP_ = 20;
|
|
|
|
//
|
|
public void tryDocking() {
|
|
if (thisEditor == null)
|
|
return;
|
|
Editor editor = thisEditor;
|
|
Frame frame = thisErrorWindow;
|
|
|
|
int ex = editor.getX();
|
|
int ey = editor.getY();
|
|
int ew = editor.getWidth();
|
|
int eh = editor.getHeight();
|
|
|
|
int fx = frame.getX();
|
|
int fy = frame.getY();
|
|
int fw = frame.getWidth();
|
|
int fh = frame.getHeight();
|
|
|
|
if (((fy > ey) && (fy < ey + eh))
|
|
|| ((fy + fh > ey) && (fy + fh < ey + eh))) {
|
|
int dis_border_left = Math.abs(ex - (fx + fw));
|
|
int dis_border_right = Math.abs((ex + ew) - (fx));
|
|
|
|
if (dis_border_left < MAX_GAP_ || dis_border_right < MAX_GAP_) {
|
|
docking_border = (dis_border_left < dis_border_right) ? 0
|
|
: 1;
|
|
dock_on_editor_y_offset_ = fy - ey;
|
|
dock();
|
|
return;
|
|
}
|
|
}
|
|
|
|
if (((fx > ex) && (fx < ex + ew))
|
|
|| ((fx + fw > ey) && (fx + fw < ex + ew))) {
|
|
int dis_border_top = Math.abs(ey - (fy + fh));
|
|
int dis_border_bot = Math.abs((ey + eh) - (fy));
|
|
|
|
if (dis_border_top < MAX_GAP_ || dis_border_bot < MAX_GAP_) {
|
|
docking_border = (dis_border_top < dis_border_bot) ? 2 : 3;
|
|
dock_on_editor_x_offset_ = fx - ex;
|
|
dock();
|
|
return;
|
|
}
|
|
}
|
|
docking_border = -1;
|
|
}
|
|
|
|
public void dock() {
|
|
if (thisEditor == null)
|
|
return;
|
|
Editor editor = thisEditor;
|
|
Frame frame = thisErrorWindow;
|
|
|
|
int ex = editor.getX();
|
|
int ey = editor.getY();
|
|
int ew = editor.getWidth();
|
|
int eh = editor.getHeight();
|
|
|
|
// int fx = frame.getX();
|
|
// int fy = frame.getY();
|
|
int fw = frame.getWidth();
|
|
int fh = frame.getHeight();
|
|
|
|
int x = 0, y = 0;
|
|
if (docking_border == -1) {
|
|
return;
|
|
}
|
|
|
|
if (docking_border == 0) {
|
|
x = ex - fw;
|
|
y = ey + dock_on_editor_y_offset_;
|
|
}
|
|
if (docking_border == 1) {
|
|
x = ex + ew;
|
|
y = ey + dock_on_editor_y_offset_;
|
|
}
|
|
|
|
if (docking_border == 2) {
|
|
x = ex + dock_on_editor_x_offset_;
|
|
y = ey - fh;
|
|
}
|
|
if (docking_border == 3) {
|
|
x = ex + dock_on_editor_x_offset_;
|
|
y = ey + eh;
|
|
}
|
|
frame.setLocation(x, y);
|
|
}
|
|
|
|
}
|
|
}
|