package nbtool.gui;
import java.awt.Color;
import java.awt.Component;
import java.awt.Font;
import java.lang.reflect.Method;
import java.util.List;
import javax.swing.JLabel;
import javax.swing.JTabbedPane;
import javax.swing.SwingUtilities;
import nbtool.data.ViewProfile;
import nbtool.data.group.Group;
import nbtool.data.log.Log;
import nbtool.gui.logviews.misc.GroupView;
import nbtool.gui.logviews.misc.ViewParent;
import nbtool.util.Center;
import nbtool.util.Center.NBToolShutdownListener;
import nbtool.util.Debug;
public class ToolDisplayTabs {
private final ToolDisplay display;
private Log current;
private static final Debug.DebugSettings debug = Debug.createSettings(Debug.WARN);
public ToolDisplayTabs(final ToolDisplay _display) {
this.display = _display;
Center.listen(new NBToolShutdownListener(){
@Override
public void nbtoolShutdownCallback() {
warnViews();
}
});
}
private void warnViews() {
for (int i = 0; i < display.displayTabs.getTabCount(); ++i) {
Component cmp = display.displayTabs.getComponentAt(i);
if (cmp instanceof ViewParent) {
((ViewParent) cmp).disappearing();
}
}
}
protected void setContents(Group group) {
current = null;
warnViews();
display.displayTabs.removeAll();
display.displayTabs.add(group.toString(), new GroupView(group));
}
protected void setContents(ViewProfile profile, Log first, List<Log> also) {
Class<? extends ViewParent>[] list = profile.viewsForLog(first);
// display.displayTabs.removeAll();
this.current = first;
warnViews();
for (int i = 0; i < list.length; ++i) {
Class<? extends ViewParent> ttype = list[i];
debug.info("creating tab %d...", i);
boolean slip = false;
boolean wrap = false;
try {
Method m = ttype.getMethod("shouldLoadInParallel");
slip = (Boolean) m.invoke(null);
m = ttype.getMethod("shouldShowInScrollPane");
wrap = (Boolean) m.invoke(null);
} catch (Exception e) {
e.printStackTrace();
debug.error("error calling method on ViewParent subclass %s: %s",
ttype.getName(), e.getMessage());
continue;
}
if (slip) {
JLabel waitLabel = new JLabel("Loading...");
waitLabel.setFont(waitLabel.getFont().deriveFont(Font.BOLD));
waitLabel.setForeground(Color.BLUE);
// display.displayTabs.addTab(ttype.getSimpleName(), waitLabel);
replace(i, ttype.getSimpleName(), ttype.getName(), waitLabel);
CreateViewRunnable cvr = new CreateViewRunnable(i, ttype, first, also);
Thread thr = new Thread(cvr);
thr.start();
} else {
CreateViewRunnable cvr = new CreateViewRunnable(i, ttype, first, also);
cvr.run();
}
}
while (list.length != display.displayTabs.getTabCount()) {
display.displayTabs.remove(display.displayTabs.getTabCount() - 1);
}
}
private final class CreateViewRunnable implements Runnable {
boolean ran = false;
int showIndex;
Class<? extends ViewParent> vClass;
ViewParent created = null;
Log first;
List<Log> also;
public CreateViewRunnable(int showIndex, Class<? extends ViewParent> vClass, Log first, List<Log> also) {
this.showIndex = showIndex;
this.vClass = vClass;
this.first = first;
this.also = also;
}
private void create() {
created = ViewParent.instantiate(vClass);
created.internal(first, also);
}
private void add() {
assert(created != null);
if (current != first) {
debug.info("CreateViewRunnable found current Log != given Log!");
return;
}
// if (index >= 0) {
// display.displayTabs.remove(index);
// }
//
// display.displayTabs.insertTab(vClass.getSimpleName(), null, created,
// vClass.getName(), index >= 0 ? index : display.displayTabs.getTabCount());
replace(showIndex, vClass.getSimpleName(), vClass.getName(), created);
created.repaint();
}
@Override
public void run() {
if (!ran) {
create();
ran = true;
if (SwingUtilities.isEventDispatchThread()) {
this.run();
} else {
SwingUtilities.invokeLater(this);
}
} else {
add();
}
}
}
private void replace(int index, String name, String tip, Component cmp) {
JTabbedPane tabs = display.displayTabs;
int used;
if (index >= 0 && index < tabs.getTabCount()) {
debug.info("replacing!");
tabs.setComponentAt(index, cmp);
used = index;
} else {
debug.info("adding!");
used = tabs.getTabCount();
tabs.add(cmp);
}
tabs.setTitleAt(used, name);
tabs.setToolTipTextAt(used, tip);
}
}