comparison java/src/uk/ac/qmul/eecs/ccmi/gui/DiagramTree.java @ 2:4b2f975e35fa

Minor Bug fixes
author Fiore Martin <fiore@eecs.qmul.ac.uk>
date Mon, 06 Feb 2012 12:54:06 +0000
parents 9418ab7b7f3f
children 9e67171477bc
comparison
equal deleted inserted replaced
1:71ff0735df5a 2:4b2f975e35fa
32 import javax.swing.JOptionPane; 32 import javax.swing.JOptionPane;
33 import javax.swing.JTree; 33 import javax.swing.JTree;
34 import javax.swing.KeyStroke; 34 import javax.swing.KeyStroke;
35 import javax.swing.event.TreeModelEvent; 35 import javax.swing.event.TreeModelEvent;
36 import javax.swing.event.TreeModelListener; 36 import javax.swing.event.TreeModelListener;
37 import javax.swing.event.TreeSelectionEvent;
38 import javax.swing.event.TreeSelectionListener;
39 import javax.swing.tree.DefaultMutableTreeNode; 37 import javax.swing.tree.DefaultMutableTreeNode;
40 import javax.swing.tree.TreeNode; 38 import javax.swing.tree.TreeNode;
41 import javax.swing.tree.TreePath; 39 import javax.swing.tree.TreePath;
42 import javax.swing.tree.TreeSelectionModel; 40 import javax.swing.tree.TreeSelectionModel;
43 41
68 collapsePath(rootPath); 66 collapsePath(rootPath);
69 selectedNodes = new ArrayList<Node>(); 67 selectedNodes = new ArrayList<Node>();
70 setEditable(false); 68 setEditable(false);
71 getSelectionModel().setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION); 69 getSelectionModel().setSelectionMode(TreeSelectionModel.SINGLE_TREE_SELECTION);
72 overwriteTreeKeystrokes(); 70 overwriteTreeKeystrokes();
73 this.addTreeSelectionListener(new TreeSelectionListener(){
74 @Override
75 public void valueChanged(TreeSelectionEvent evt) {
76 if(treeSelectionListenerGateOpen){
77 final DiagramModelTreeNode treeNode = (DiagramModelTreeNode)evt.getPath().getLastPathComponent();
78 if(treeNode instanceof DiagramElement){
79 SoundFactory.getInstance().play(((DiagramElement)treeNode).getSound(), new PlayerListener(){
80 @Override
81 public void playEnded() {
82 NarratorFactory.getInstance().speak(treeNode.spokenText());
83 }
84 });
85 }else{
86 NarratorFactory.getInstance().speak(treeNode.spokenText());
87 }
88 }
89 }
90 });
91 /* don't use the swing focus system as we provide one on our own */ 71 /* don't use the swing focus system as we provide one on our own */
92 setFocusTraversalKeysEnabled(false); 72 setFocusTraversalKeysEnabled(false);
93 getAccessibleContext().setAccessibleName(""); 73 getAccessibleContext().setAccessibleName("");
94 } 74 }
95 75
166 * to the related edge/node itself 146 * to the related edge/node itself
167 */ 147 */
168 public void jump(JumpTo jumpTo){ 148 public void jump(JumpTo jumpTo){
169 final Narrator narrator = NarratorFactory.getInstance(); 149 final Narrator narrator = NarratorFactory.getInstance();
170 TreePath oldPath; 150 TreePath oldPath;
171 treeSelectionListenerGateOpen = false;
172 switch(jumpTo){ 151 switch(jumpTo){
173 case REFERENCE : 152 case REFERENCE :
174 oldPath = getSelectionPath(); 153 oldPath = getSelectionPath();
175 DiagramModelTreeNode selectedTreeNode = (DiagramModelTreeNode)oldPath.getLastPathComponent(); 154 DiagramModelTreeNode selectedTreeNode = (DiagramModelTreeNode)oldPath.getLastPathComponent();
176 if(selectedTreeNode instanceof NodeReferenceMutableTreeNode){ 155 if(selectedTreeNode instanceof NodeReferenceMutableTreeNode){
248 initialValue); 227 initialValue);
249 if(selectedValue == null){ 228 if(selectedValue == null){
250 /* it speaks anyway as we set up the playerListener in the EditorFrame class. No need to use narrator then */ 229 /* it speaks anyway as we set up the playerListener in the EditorFrame class. No need to use narrator then */
251 SoundFactory.getInstance().play(SoundEvent.CANCEL); 230 SoundFactory.getInstance().play(SoundEvent.CANCEL);
252 InteractionLog.log(INTERACTIONLOG_SOURCE,"cancel select type to jump dialog",""); 231 InteractionLog.log(INTERACTIONLOG_SOURCE,"cancel select type to jump dialog","");
253 treeSelectionListenerGateOpen = true;
254 return; 232 return;
255 } 233 }
256 /* we search in the root which type tree node has getName() equal to the selected one */ 234 /* we search in the root which type tree node has getName() equal to the selected one */
257 TypeMutableTreeNode typeNode = null; 235 TypeMutableTreeNode typeNode = null;
258 for(int i = 0; i< root.getChildCount(); i++){ 236 for(int i = 0; i< root.getChildCount(); i++){
277 255
278 if(treeModel.getBookmarks().size() == 0){ 256 if(treeModel.getBookmarks().size() == 0){
279 SoundFactory.getInstance().play(SoundEvent.ERROR ,new PlayerListener(){ 257 SoundFactory.getInstance().play(SoundEvent.ERROR ,new PlayerListener(){
280 @Override 258 @Override
281 public void playEnded() { 259 public void playEnded() {
282 narrator.speak("speech.no_bookmarks"); 260 narrator.speak(resources.getString("speech.no_bookmarks"));
283 } 261 }
284 }); 262 });
285 InteractionLog.log(INTERACTIONLOG_SOURCE,"no bookmarks available",""); 263 InteractionLog.log(INTERACTIONLOG_SOURCE,"no bookmarks available","");
286 treeSelectionListenerGateOpen = true;
287 return; 264 return;
288 } 265 }
289 266
290 String[] bookmarkArray = new String[treeModel.getBookmarks().size()]; 267 String[] bookmarkArray = new String[treeModel.getBookmarks().size()];
291 bookmarkArray = treeModel.getBookmarks().toArray(bookmarkArray); 268 bookmarkArray = treeModel.getBookmarks().toArray(bookmarkArray);
313 InteractionLog.log(INTERACTIONLOG_SOURCE,"bookmark selected",bookmark); 290 InteractionLog.log(INTERACTIONLOG_SOURCE,"bookmark selected",bookmark);
314 }else{ 291 }else{
315 /* it speaks anyway, as we set up the speech in the EditorFrame class. no need to use the narrator then */ 292 /* it speaks anyway, as we set up the speech in the EditorFrame class. no need to use the narrator then */
316 SoundFactory.getInstance().play(SoundEvent.CANCEL); 293 SoundFactory.getInstance().play(SoundEvent.CANCEL);
317 InteractionLog.log(INTERACTIONLOG_SOURCE,"cancel select bookmark dialog",""); 294 InteractionLog.log(INTERACTIONLOG_SOURCE,"cancel select bookmark dialog","");
318 treeSelectionListenerGateOpen = true;
319 return; 295 return;
320 } 296 }
321 break; 297 break;
322 298
323 } 299 }
324 InteractionLog.log(INTERACTIONLOG_SOURCE,"jumped to "+jumpTo.toString(),((DiagramModelTreeNode)getSelectionPath().getLastPathComponent()).getName()); 300 InteractionLog.log(INTERACTIONLOG_SOURCE,"jumped to "+jumpTo.toString(),((DiagramModelTreeNode)getSelectionPath().getLastPathComponent()).getName());
325 SoundFactory.getInstance().play(SoundEvent.JUMP); 301 SoundFactory.getInstance().play(SoundEvent.JUMP);
326 treeSelectionListenerGateOpen = true;
327 } 302 }
328 303
329 public void jumpTo(final DiagramElement de){ 304 public void jumpTo(final DiagramElement de){
330 TreePath oldPath = getSelectionPath(); 305 TreePath oldPath = getSelectionPath();
331 collapseAll((DiagramModelTreeNode)oldPath.getLastPathComponent(),de); 306 collapseAll((DiagramModelTreeNode)oldPath.getLastPathComponent(),de);
332 setSelectionPath(new TreePath(de.getPath())); 307 setSelectionPath(new TreePath(de.getPath()));
333 treeSelectionListenerGateOpen = false;
334 SoundFactory.getInstance().play( SoundEvent.JUMP, new PlayerListener(){ 308 SoundFactory.getInstance().play( SoundEvent.JUMP, new PlayerListener(){
335 @Override 309 @Override
336 public void playEnded() { 310 public void playEnded() {
337 NarratorFactory.getInstance().speak(MessageFormat.format(resources.getString("speech.jump"),de.spokenText())); 311 NarratorFactory.getInstance().speak(MessageFormat.format(resources.getString("speech.jump"),de.spokenText()));
338 } 312 }
339 }); 313 });
340 treeSelectionListenerGateOpen = true;
341 } 314 }
342 315
343 /* collapse all the nodes in the path from "from" to "to" upwards(with the same direction as going from a leaf to the root)*/ 316 /* collapse all the nodes in the path from "from" to "to" upwards(with the same direction as going from a leaf to the root)*/
344 private void collapseAll(DiagramModelTreeNode from, DiagramModelTreeNode to){ 317 private void collapseAll(DiagramModelTreeNode from, DiagramModelTreeNode to){
345 DiagramModelTreeNode currentNode = from; 318 DiagramModelTreeNode currentNode = from;
350 } 323 }
351 324
352 @Override 325 @Override
353 protected void processMouseEvent(MouseEvent e){ 326 protected void processMouseEvent(MouseEvent e){
354 //do nothing as the tree does not have to be editable with mouse 327 //do nothing as the tree does not have to be editable with mouse
328 }
329
330 @Override
331 protected void processKeyEvent(KeyEvent e){
332 /* allow only cursor keys, tab key, delete, and actions (CTRL+something) */
333 if(e.getKeyChar() == KeyEvent.CHAR_UNDEFINED
334 || e.getKeyCode() == KeyEvent.VK_TAB
335 || e.getKeyCode() == KeyEvent.VK_SPACE
336 || e.getKeyCode() == KeyEvent.VK_DELETE
337 || e.isControlDown()
338 || e.isAltDown())
339 super.processKeyEvent(e);
355 } 340 }
356 341
357 private void overwriteTreeKeystrokes() { 342 private void overwriteTreeKeystrokes() {
358 /* overwrite the keys. up and down arrow are overwritten so that it loops when the top and the */ 343 /* overwrite the keys. up and down arrow are overwritten so that it loops when the top and the */
359 /* bottom are reached rather than getting stuck */ 344 /* bottom are reached rather than getting stuck */
373 nextTreeNode = treeNode; 358 nextTreeNode = treeNode;
374 else /* loop = go to first child of own parent */ 359 else /* loop = go to first child of own parent */
375 nextTreeNode = (DiagramModelTreeNode)parent.getFirstChild(); 360 nextTreeNode = (DiagramModelTreeNode)parent.getFirstChild();
376 loop = SoundEvent.LIST_BOTTOM_REACHED; 361 loop = SoundEvent.LIST_BOTTOM_REACHED;
377 } 362 }
378 treeSelectionListenerGateOpen = false;
379 setSelectionPath(new TreePath(nextTreeNode.getPath())); 363 setSelectionPath(new TreePath(nextTreeNode.getPath()));
380 final InputStream finalSound = getTreeNodeSound(nextTreeNode); 364 final InputStream finalSound = getTreeNodeSound(nextTreeNode);
381 final String currentPathSpeech = currentPathSpeech(); 365 final String currentPathSpeech = currentPathSpeech();
382 SoundFactory.getInstance().play(loop, new PlayerListener(){ 366 SoundFactory.getInstance().play(loop, new PlayerListener(){
383 public void playEnded() { 367 public void playEnded() {
384 SoundFactory.getInstance().play(finalSound); 368 SoundFactory.getInstance().play(finalSound);
385 NarratorFactory.getInstance().speak(currentPathSpeech); 369 NarratorFactory.getInstance().speak(currentPathSpeech);
386 } 370 }
387 }); 371 });
388 treeSelectionListenerGateOpen = true;
389 InteractionLog.log(INTERACTIONLOG_SOURCE,"move down",nextTreeNode.toString()); 372 InteractionLog.log(INTERACTIONLOG_SOURCE,"move down",nextTreeNode.toString());
390 }}); 373 }});
391 374
392 getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_UP,0),"up"); 375 getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_UP,0),"up");
393 getActionMap().put("up", new AbstractAction(){ 376 getActionMap().put("up", new AbstractAction(){
402 previousTreeNode = treeNode; 385 previousTreeNode = treeNode;
403 else 386 else
404 previousTreeNode = (DiagramModelTreeNode)parent.getLastChild(); 387 previousTreeNode = (DiagramModelTreeNode)parent.getLastChild();
405 loop = SoundEvent.LIST_TOP_REACHED; 388 loop = SoundEvent.LIST_TOP_REACHED;
406 } 389 }
407 treeSelectionListenerGateOpen = false;
408 setSelectionPath(new TreePath(previousTreeNode.getPath())); 390 setSelectionPath(new TreePath(previousTreeNode.getPath()));
409 final InputStream finalSound = getTreeNodeSound(previousTreeNode); 391 final InputStream finalSound = getTreeNodeSound(previousTreeNode);
410 final String currentPathSpeech = currentPathSpeech(); 392 final String currentPathSpeech = currentPathSpeech();
411 SoundFactory.getInstance().play(loop, new PlayerListener(){ 393 SoundFactory.getInstance().play(loop, new PlayerListener(){
412 public void playEnded() { 394 public void playEnded() {
413 SoundFactory.getInstance().play(finalSound); 395 SoundFactory.getInstance().play(finalSound);
414 NarratorFactory.getInstance().speak(currentPathSpeech); 396 NarratorFactory.getInstance().speak(currentPathSpeech);
415 } 397 }
416 }); 398 });
417 treeSelectionListenerGateOpen = true;
418 InteractionLog.log(INTERACTIONLOG_SOURCE,"move up",previousTreeNode.toString()); 399 InteractionLog.log(INTERACTIONLOG_SOURCE,"move up",previousTreeNode.toString());
419 }}); 400 }});
420 401
421 getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT,0),"right"); 402 getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT,0),"right");
422 getActionMap().put("right", new AbstractAction(){ 403 getActionMap().put("right", new AbstractAction(){
427 if(treeNode.isLeaf()){ 408 if(treeNode.isLeaf()){
428 notifyBorderReached(treeNode); 409 notifyBorderReached(treeNode);
429 InteractionLog.log(INTERACTIONLOG_SOURCE,"move right","border reached"); 410 InteractionLog.log(INTERACTIONLOG_SOURCE,"move right","border reached");
430 } 411 }
431 else{ 412 else{
432 treeSelectionListenerGateOpen = false;
433 expandPath(path); 413 expandPath(path);
434 setSelectionPath(new TreePath(((DiagramModelTreeNode)treeNode.getFirstChild()).getPath())); 414 setSelectionPath(new TreePath(((DiagramModelTreeNode)treeNode.getFirstChild()).getPath()));
435 final String currentPathSpeech = currentPathSpeech(); 415 final String currentPathSpeech = currentPathSpeech();
436 SoundFactory.getInstance().play(SoundEvent.TREE_NODE_EXPAND,new PlayerListener(){ 416 SoundFactory.getInstance().play(SoundEvent.TREE_NODE_EXPAND,new PlayerListener(){
437 @Override 417 @Override
438 public void playEnded() { 418 public void playEnded() {
439 NarratorFactory.getInstance().speak(currentPathSpeech); 419 NarratorFactory.getInstance().speak(currentPathSpeech);
440 } 420 }
441 }); 421 });
442 treeSelectionListenerGateOpen = true;
443 InteractionLog.log(INTERACTIONLOG_SOURCE,"move right",((DiagramModelTreeNode)treeNode.getFirstChild()).toString()); 422 InteractionLog.log(INTERACTIONLOG_SOURCE,"move right",((DiagramModelTreeNode)treeNode.getFirstChild()).toString());
444 } 423 }
445 } 424 }
446 }); 425 });
447 426
455 if(parent == null){/* root node */ 434 if(parent == null){/* root node */
456 notifyBorderReached(treeNode); 435 notifyBorderReached(treeNode);
457 InteractionLog.log(INTERACTIONLOG_SOURCE,"move left","border reached"); 436 InteractionLog.log(INTERACTIONLOG_SOURCE,"move left","border reached");
458 } 437 }
459 else{ 438 else{
460 treeSelectionListenerGateOpen = false;
461 TreePath newPath = new TreePath(((DiagramModelTreeNode)parent).getPath()); 439 TreePath newPath = new TreePath(((DiagramModelTreeNode)parent).getPath());
462 setSelectionPath(newPath); 440 setSelectionPath(newPath);
463 collapsePath(newPath); 441 collapsePath(newPath);
464 final String currentPathSpeech = currentPathSpeech(); 442 final String currentPathSpeech = currentPathSpeech();
465 SoundFactory.getInstance().play(SoundEvent.TREE_NODE_COLLAPSE,new PlayerListener(){ 443 SoundFactory.getInstance().play(SoundEvent.TREE_NODE_COLLAPSE,new PlayerListener(){
467 public void playEnded() { 445 public void playEnded() {
468 NarratorFactory.getInstance().speak(currentPathSpeech); 446 NarratorFactory.getInstance().speak(currentPathSpeech);
469 } 447 }
470 }); 448 });
471 InteractionLog.log(INTERACTIONLOG_SOURCE,"move left",((DiagramModelTreeNode)parent).toString()); 449 InteractionLog.log(INTERACTIONLOG_SOURCE,"move left",((DiagramModelTreeNode)parent).toString());
472 treeSelectionListenerGateOpen = true;
473 } 450 }
474 } 451 }
475 }); 452 });
476 453
477 getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_SPACE,0),"space"); 454 getInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_SPACE,0),"space");
600 577
601 578
602 private List<Node> selectedNodes; 579 private List<Node> selectedNodes;
603 private Diagram diagram; 580 private Diagram diagram;
604 private ResourceBundle resources; 581 private ResourceBundle resources;
605 private boolean treeSelectionListenerGateOpen;
606 private static final char SELECTED_NODE_MARK_BEGIN = '<'; 582 private static final char SELECTED_NODE_MARK_BEGIN = '<';
607 private static final char SELECTED_NODE_MARK_END = '>'; 583 private static final char SELECTED_NODE_MARK_END = '>';
608 private static final String INTERACTIONLOG_SOURCE = "TREE"; 584 private static final String INTERACTIONLOG_SOURCE = "TREE";
609 static enum JumpTo {REFERENCE, ROOT, TYPE, SELECTED_TYPE, BOOKMARK} 585 static enum JumpTo {REFERENCE, ROOT, TYPE, SELECTED_TYPE, BOOKMARK}
610 586