diff options
| author | Fuwn <[email protected]> | 2026-02-12 22:33:32 -0800 |
|---|---|---|
| committer | Fuwn <[email protected]> | 2026-02-12 22:33:32 -0800 |
| commit | c7a9d4a6bd53ed7d61731770f2f10e8b9fd435f9 (patch) | |
| tree | df9f48bf128a6c0186a8e91857d6ff30fe0e9f18 /NET/worlds/scape/EditTile.java | |
| download | worldsplayer-c7a9d4a6bd53ed7d61731770f2f10e8b9fd435f9.tar.xz worldsplayer-c7a9d4a6bd53ed7d61731770f2f10e8b9fd435f9.zip | |
Initial commit
Diffstat (limited to 'NET/worlds/scape/EditTile.java')
| -rw-r--r-- | NET/worlds/scape/EditTile.java | 664 |
1 files changed, 664 insertions, 0 deletions
diff --git a/NET/worlds/scape/EditTile.java b/NET/worlds/scape/EditTile.java new file mode 100644 index 0000000..d0ab600 --- /dev/null +++ b/NET/worlds/scape/EditTile.java @@ -0,0 +1,664 @@ +package NET.worlds.scape; + +import NET.worlds.console.Console; +import NET.worlds.console.DialogDisabled; +import NET.worlds.console.DialogReceiver; +import NET.worlds.console.ExposedPanel; +import NET.worlds.console.Main; +import NET.worlds.console.MainCallback; +import NET.worlds.console.PolledDialog; +import NET.worlds.console.RenderCanvas; +import NET.worlds.console.SnapTool; +import NET.worlds.console.Tree; +import NET.worlds.console.TreeCallback; +import NET.worlds.network.URL; +import java.awt.Button; +import java.awt.Component; +import java.awt.GridBagConstraints; +import java.awt.GridBagLayout; +import java.awt.Label; +import java.awt.Point; +import java.io.IOException; +import java.text.MessageFormat; +import java.util.Enumeration; +import java.util.Vector; + +public class EditTile extends ExposedPanel implements DialogReceiver, TreeCallback, MainCallback, DialogDisabled { + private Button editButton = new Button(Console.message("Edit")); + private Button addButton = new Button(Console.message("Add")); + private Button delButton = new Button(Console.message("Delete")); + private Button helpButton = new Button(Console.message("Help")); + private ToolBar toolbar = new ToolBar(); + private Label title = new Label(); + private String titleText = ""; + private boolean usingTitleAsPrompt; + private PropList props = new PropList(); + private int queuedFunction = 0; + private Object queuedObject; + private Tree tree; + private PolledDialog activePopup; + private boolean startup = true; + private World rootWorld = null; + private boolean isDialogDisabled; + private static final int NONE = 0; + private static final int DELETE = 1; + private static final int ADD = 2; + private static final int CHANGE = 3; + private static final int UPDATE = 4; + private static final int CUT = 5; + private static final int COPY = 6; + private static final int PASTE = 7; + private static final int UNDO = 8; + private static final int EDIT = 9; + private static final int DROP = 10; + private static final int HELP = 11; + private static ClipboardEntry clipboard; + private static UndoStack undoStack = new UndoStack(); + private Undoable preAddStackTop; + private boolean isAdd; + private SendURLAction helpAction = new SendURLAction(); + private Persister helpBrowser; + + public void viewProperties(Object obj) { + Console.getFrame().setShaperVisible(true); + this.queue(3, obj); + } + + public void libraryDrop(URL url, String propertyName, Component comp, Point location) { + this.queue(10, new DropInfo(url, propertyName, comp, location)); + } + + public EditTile(Tree tree) { + this.tree = tree; + tree.setOwner(this); + GridBagLayout gbag = new GridBagLayout(); + this.setLayout(gbag); + GridBagConstraints c = new GridBagConstraints(); + c.fill = 2; + c.gridwidth = 0; + c.weightx = 1.0; + c.weighty = 0.0; + c.anchor = 18; + this.add(gbag, this.toolbar, c); + this.add(gbag, this.title, c); + c.weighty = 1.0; + c.fill = 1; + c.gridwidth = 2; + c.gridheight = 0; + this.add(gbag, this.props, c); + c.weightx = 0.0; + c.weighty = 0.0; + c.gridwidth = 0; + c.gridheight = 1; + c.fill = 2; + this.add(gbag, this.editButton, c); + this.add(gbag, this.addButton, c); + this.add(gbag, this.delButton, c); + this.add(gbag, this.helpButton, c); + Main.register(this); + } + + public void update() { + this.queue(4); + } + + private void add(GridBagLayout gbag, Component comp, GridBagConstraints c) { + gbag.setConstraints(comp, c); + this.add(comp); + } + + private boolean queue(int function) { + return this.queue(function, null); + } + + private synchronized boolean queue(int function, Object obj) { + if (this.queuedFunction == 0 && this.activePopup == null) { + this.queuedFunction = function; + this.queuedObject = obj; + this.disable(); + } + + return true; + } + + @Override + public synchronized void mainCallback() { + if (this.startup) { + World w = Pilot.getActiveWorld(); + if (w != null) { + this.change(w); + this.startup = false; + } + } + + if (this.rootWorld != null) { + this.rootWorld.incRef(); + } + + boolean enable = true; + switch (this.queuedFunction) { + case 0: + return; + case 1: + this.delete(false); + break; + case 2: + enable = this.doAdd(); + break; + case 3: + this.change(this.queuedObject); + break; + case 4: + this.tree.update(); + break; + case 5: + this.delete(true); + break; + case 6: + this.doCopy(); + break; + case 7: + this.doPaste(); + break; + case 8: + this.doUndo(); + break; + case 9: + enable = this.doEdit(); + break; + case 10: + if (!this.drop((DropInfo)this.queuedObject)) { + Object[] arguments = new Object[]{new String("" + ((DropInfo)this.queuedObject).url)}; + Console.println(MessageFormat.format(Console.message("Target-doesnt"), arguments)); + } + break; + case 11: + this.doHelp(); + } + + this.enable(enable); + this.queuedFunction = 0; + this.queuedObject = null; + } + + private void delete(boolean isCut) { + if (this.delButton.isEnabled()) { + PropTreeNode e = (PropTreeNode)this.tree.getSelectedNode(); + if (e != null && this.tree.hasFocus()) { + this.addUndoable(e.delete(isCut)); + } else { + Property p = this.props.getSelectedProperty(); + + assert p.canSetNull() && p.get() != null; + + this.addUndoableSet(p, null); + } + + this.tree.update(); + } + } + + public static void adjustDroppedSource(SuperRoot sr) { + if (sr != null && (!(sr instanceof WObject) || !((WObject)sr).isDynamic())) { + sr.setSourceURL(null); + } + } + + private boolean drop(DropInfo info) { + Object dropped = info.url; + if (info.url.endsWith(".class") || info.url.endsWith("." + WObject.getSaveExtension())) { + SuperRoot sr = WobLoader.immediateLoad(info.url); + adjustDroppedSource(sr); + dropped = sr; + } + + return this.drop(dropped, info.propertyName, false, info.comp, info.location); + } + + private boolean drop(Object obj, String propertyName, boolean isPaste) { + return this.drop(obj, propertyName, isPaste, null, null); + } + + private boolean drop(Object obj, String propertyName, boolean isPaste, Component comp, Point location) { + if (obj == null) { + return false; + } else { + PropTreeNode e = null; + Point3Temp dropPoint = null; + if (comp == null && this.tree.hasFocus()) { + e = (PropTreeNode)this.tree.getSelectedNode(); + } else if (comp == this.tree) { + e = (PropTreeNode)this.tree.elementAt(location); + } else if (comp instanceof RenderCanvas) { + Camera c = ((RenderCanvas)comp).getCamera(); + dropPoint = Point3Temp.make(); + WObject picked = c.getObjectAt(location.x, location.y, false, dropPoint); + if (picked != null) { + if (obj instanceof WObject) { + picked = picked.getRoom(); + } + } else { + Pilot pilot = Pilot.getActive(); + picked = pilot.getRoom(); + dropPoint.set(0.0F, 180.0F, 0.0F); + dropPoint.times(pilot); + } + + if (picked != null) { + this.change(picked); + e = (PropTreeNode)this.tree.getSelectedNode(); + } + } + + if (e == null) { + return false; + } else { + boolean success = false; + VectorProperty vp; + PropAdder adder; + if ((vp = e.getContainingVectorProperty()) != null && (adder = vp.getAdder()) != null) { + success = adder.libraryDrop(this, obj, isPaste, true); + } + + if (!success) { + Object top; + for (top = null; e != null; e = (PropTreeNode)e.getParent()) { + top = e.getObject(); + if (top instanceof Properties) { + break; + } + + if (top instanceof Property) { + Property prop = (Property)top; + top = ((Property)top).get(); + if (top instanceof Properties) { + break; + } + } + } + + if (e != null) { + Vector targets = new Vector(); + int topLevelTargets = this.recurseFindDropTargets(targets, obj, propertyName, isPaste, new EnumProperties(top), 0, 10); + if (topLevelTargets == 1 || topLevelTargets == 0 && targets.size() == 1) { + success = ((LibraryDrop)targets.elementAt(0)).libraryDrop(this, obj, isPaste, true); + } + } + } + + if (success) { + if (obj instanceof Properties) { + this.change(obj); + } else { + this.tree.update(); + } + } + + WObject wobj; + if (dropPoint != null && obj instanceof WObject && !(obj instanceof Room) && (wobj = (WObject)obj).isActive()) { + dropPoint.z = wobj.getZ(); + wobj.moveTo(SnapTool.snapTool().snapTo(dropPoint)); + } + + return success; + } + } + } + + private int recurseFindDropTargets(Vector targets, Object obj, String propertyName, boolean isPaste, Enumeration props, int level, int maxLevel) { + int firstLevelMatches = 0; + if (level > maxLevel) { + return 0; + } else { + while (props.hasMoreElements()) { + Property p = (Property)props.nextElement(); + boolean propMatch = propertyName == null || propertyName.equals(p.getName()); + if (propMatch) { + LibraryDrop target = null; + if (p instanceof VectorProperty) { + target = ((VectorProperty)p).getAdder(); + } else { + target = p.getEditor(); + } + + if (target != null && target.libraryDrop(this, obj, isPaste, false)) { + if (level == 0) { + targets.insertElementAt(target, firstLevelMatches++); + } else { + targets.addElement(target); + } + continue; + } + } + + if (!(p instanceof VectorProperty)) { + int err = this.recurseFindDropTargets(targets, obj, propertyName, isPaste, new EnumProperties(p.get()), level + 1, maxLevel); + if (err != 0) { + return err; + } + } + } + + return firstLevelMatches; + } + } + + private boolean change(Object obj) { + Object parent = obj; + Vector lineage = new Vector(); + + Object p; + while (parent instanceof Properties && (p = ((Properties)parent).propertyParent()) != null) { + if (lineage != null) { + Enumeration e = new EnumProperties(p); + boolean found = false; + + while (e.hasMoreElements()) { + Property prop = (Property)e.nextElement(); + Object o = prop.get(); + boolean isVector = prop instanceof VectorProperty; + if (o == parent || isVector && o != null && ((Vector)o).indexOf(parent) != -1) { + if (isVector) { + lineage.insertElementAt(parent, 0); + } + + lineage.insertElementAt(prop, 0); + found = true; + break; + } + } + + if (!found) { + lineage = null; + } + } + + parent = p; + } + + this.rootWorld = null; + if (parent instanceof World) { + this.rootWorld = (World)parent; + } + + PropTreeNode root = new PropTreeNode(parent); + if (lineage != null) { + this.tree.change(root, lineage); + } else { + this.tree.change(root, obj); + } + + return true; + } + + @Override + public void treeFocusChanged(boolean hasFocus) { + if (hasFocus) { + this.props.deselect(this.props.getSelectedIndex()); + this.adjustButtons(); + } + } + + @Override + public void treeChange(Object obj) { + if (obj instanceof Property && !(obj instanceof VectorProperty)) { + obj = ((Property)obj).get(); + } + + this.props.setObject(obj); + this.toolbar.setCurrentObject(obj); + String name = obj.getClass().getName(); + int index; + if ((index = name.lastIndexOf(46)) != -1) { + name = name.substring(index + 1); + } + + this.setTitle(name + " " + Console.message("Properties")); + this.adjustButtons(); + } + + private void setTitle(String titleText) { + this.titleText = titleText; + if (!this.usingTitleAsPrompt) { + this.title.setText(titleText); + } + } + + public void setPrompt(String promptText) { + this.title.setText((this.usingTitleAsPrompt = promptText != null) ? promptText : this.titleText); + } + + private void adjustButtons() { + PropTreeNode e = (PropTreeNode)this.tree.getSelectedNode(); + if (e != null && this.tree.hasFocus()) { + this.editButton.enable(e.canEdit()); + this.delButton.enable(e.canDelete()); + this.addButton.enable(e.canAdd()); + this.helpButton.enable(true); + } else { + Property p = this.props.getSelectedProperty(); + if (p != null) { + Object obj = p.get(); + this.editButton.enable(p.getEditor() != null); + this.delButton.enable(p.canSetNull() && obj != null); + this.addButton.enable(p.canSetNull() && p.getEditor() != null && obj == null); + this.helpButton.enable(p.helpExists); + } else { + this.editButton.disable(); + this.delButton.disable(); + this.addButton.disable(); + this.helpButton.disable(); + } + } + } + + @Override + public void dialogDisable(boolean disable) { + this.isDialogDisabled = disable; + this.toolbar.dialogDisable(disable); + } + + @Override + public boolean handleEvent(java.awt.Event event) { + if (event.id == 701) { + if (event.target == this.props) { + this.tree.setFocus(false); + } + + this.adjustButtons(); + } + + return this.isDialogDisabled ? false : super.handleEvent(event); + } + + @Override + public boolean action(java.awt.Event event, Object what) { + Object target = event.target; + if (target == this.delButton) { + return this.queue(1); + } else if (target == this.addButton) { + return this.queue(2); + } else if (target != this.editButton && (target != this.props || !this.editButton.isEnabled())) { + return target == this.helpButton ? this.queue(11) : false; + } else { + return this.queue(9); + } + } + + @Override + public void dialogDone(Object who, boolean confirmed) { + if (who == this.activePopup) { + this.activePopup = null; + this.tree.enable(); + if (confirmed) { + Undoable u; + Object obj; + if (this.isAdd + && (u = undoStack.peek()) != this.preAddStackTop + && u instanceof UndoablAdd + && (obj = ((UndoablAdd)u).getObject()) instanceof Properties) { + this.change(obj); + } else { + this.tree.update(); + } + } + + this.enable(); + } + } + + private boolean doEdit() { + Property p = this.props.getSelectedProperty(); + PropEditor editor; + if (p != null && (editor = p.getEditor()) != null) { + this.isAdd = false; + this.activePopup = editor.edit(this, "Edit " + p.getName()); + this.tree.disable(); + return false; + } else { + return true; + } + } + + private boolean doAdd() { + PropTreeNode e = (PropTreeNode)this.tree.getSelectedNode(); + PropAdder adder; + if (e != null && this.tree.hasFocus() && (adder = e.getAdder()) != null) { + this.preAddStackTop = undoStack.peek(); + this.isAdd = true; + this.activePopup = adder.add(this, "Add to " + e.getContainerName()); + this.tree.disable(); + return false; + } else { + return true; + } + } + + public void cut() { + this.queue(5); + } + + public void paste() { + this.queue(7); + } + + private boolean doPaste() { + if (clipboard != null) { + SuperRoot obj = clipboard.paste(); + if (this.drop(obj, null, true)) { + return true; + } + + clipboard.unPaste(obj); + Console.println(Console.message("Clip-contents")); + } else { + Console.println(Console.message("Clip-empty")); + } + + return false; + } + + private boolean doHelp() { + this.helpAction.showDialog = false; + if (this.tree.hasFocus() && this.props.getSelectedProperty() == null) { + try { + SuperRoot s = (SuperRoot)((PropTreeNode)this.tree.getSelectedNode()).getObject(); + if (s != null) { + this.helpAction.setDestination(s.getHelpURL()); + } + } catch (ClassCastException var5) { + Console.println(Console.message("No-help")); + } + } else { + Property p = this.props.getSelectedProperty(); + if (p != null && p.helpExists) { + try { + SuperRoot s = (SuperRoot)((PropTreeNode)this.tree.getSelectedNode()).getObject(); + if (s != null) { + this.helpAction.setDestination(s.getHelpURL(p)); + } + } catch (ClassCastException var4) { + Console.println(Console.message("No-help")); + } + } + } + + this.helpBrowser = this.helpAction.trigger(null, this.helpBrowser); + return true; + } + + public void copy() { + this.queue(6); + } + + private void doCopy() { + SuperRoot item = this.getCurSuperRoot(true); + if (item != null) { + ClipboardEntry newClip = new ClipboardEntry(); + if (newClip.copy(item)) { + this.addUndoable(new UndoabCopy(newClip)); + } + } + } + + public boolean save(String fileName) { + SuperRoot item = this.getCurSuperRoot(true); + + try { + item.saveFile(new URL(URL.getCurDir(), fileName)); + return true; + } catch (IOException var4) { + return false; + } + } + + private SuperRoot getCurSuperRoot(boolean allowContainers) { + Object obj = this.props.getObject(); + return obj instanceof SuperRoot ? (SuperRoot)obj : null; + } + + public void addUndoable(Undoable u) { + undoStack.push(u); + } + + public void addUndoableSet(Property prop, Object obj) { + this.addUndoable(new UndoablSet(prop, obj)); + } + + public void addUndoableAdd(VectorProperty prop, Object obj, boolean changeTree) { + this.addUndoable(new UndoablAdd(prop, obj)); + if (!changeTree) { + this.preAddStackTop = undoStack.peek(); + } + } + + public void addUndoablePaste(VectorProperty prop, Object obj) { + try { + this.addUndoable(new UndoablPaste(prop, clipboard, obj)); + } catch (Error var4) { + Console.println(var4.getMessage()); + } + } + + public void undo() { + if (Main.isMainThread()) { + this.doUndo(); + } else { + this.queue(8); + } + } + + private void doUndo() { + if (undoStack.undo()) { + this.tree.update(); + } + } + + public static void setClipboard(ClipboardEntry clip) { + clipboard = clip; + } + + public static ClipboardEntry getClipboard() { + return clipboard; + } +} |