1 11 12 package org.eclipse.ant.internal.ui.editor.text; 13 14 import java.util.ArrayList ; 15 import java.util.HashMap ; 16 import java.util.HashSet ; 17 import java.util.Iterator ; 18 import java.util.List ; 19 import java.util.Map ; 20 import java.util.Set ; 21 22 import org.eclipse.ant.internal.ui.editor.AntEditor; 23 import org.eclipse.ant.internal.ui.model.AntElementNode; 24 import org.eclipse.ant.internal.ui.model.AntModel; 25 import org.eclipse.ant.internal.ui.model.AntProjectNode; 26 import org.eclipse.jface.text.BadLocationException; 27 import org.eclipse.jface.text.IDocument; 28 import org.eclipse.jface.text.Position; 29 import org.eclipse.jface.text.source.Annotation; 30 import org.eclipse.jface.text.source.projection.ProjectionAnnotation; 31 import org.eclipse.jface.text.source.projection.ProjectionAnnotationModel; 32 33 public class AntFoldingStructureProvider { 34 35 private AntEditor fEditor; 36 private IDocument fDocument; 37 38 41 private Map fPositionToElement= new HashMap (); 42 43 public AntFoldingStructureProvider(AntEditor editor) { 44 super(); 45 fEditor = editor; 46 } 47 48 private void updateFoldingRegions(ProjectionAnnotationModel model, Set currentRegions) { 49 Annotation[] deletions = computeDifferences(model, currentRegions); 50 51 Map additionsMap = new HashMap (); 52 for (Iterator iter = currentRegions.iterator(); iter.hasNext();) { 53 Object position= iter.next(); 54 AntElementNode node= (AntElementNode)fPositionToElement.get(position); 55 additionsMap.put(new ProjectionAnnotation(node.collapseProjection()), position); 56 } 57 58 if ((deletions.length != 0 || additionsMap.size() != 0)) { 59 model.modifyAnnotations(deletions, additionsMap, new Annotation[] {}); 60 } 61 } 62 63 private Annotation[] computeDifferences(ProjectionAnnotationModel model, Set additions) { 64 List deletions = new ArrayList (); 65 for (Iterator iter = model.getAnnotationIterator(); iter.hasNext();) { 66 Object annotation = iter.next(); 67 if (annotation instanceof ProjectionAnnotation) { 68 Position position = model.getPosition((Annotation) annotation); 69 if (additions.contains(position)) { 70 additions.remove(position); 71 } else { 72 deletions.add(annotation); 73 } 74 } 75 } 76 return (Annotation[]) deletions.toArray(new Annotation[deletions.size()]); 77 } 78 79 public void updateFoldingRegions(AntModel antModel) { 80 fPositionToElement= new HashMap (); 81 try { 82 ProjectionAnnotationModel model = (ProjectionAnnotationModel) fEditor.getAdapter(ProjectionAnnotationModel.class); 83 if (model == null) { 84 return; 85 } 86 87 Set currentRegions= new HashSet (); 88 AntProjectNode node= antModel.getProjectNode(); 89 if (node == null || node.getOffset() == -1 || node.getLength() == -1) { 90 return; 91 } 92 List root= new ArrayList (2); 93 root.add(node); 94 List nodes= antModel.getNonStructuralNodes(); 95 root.addAll(nodes); 96 addFoldingRegions(currentRegions, root); 97 updateFoldingRegions(model, currentRegions); 98 } catch (BadLocationException be) { 99 } 101 } 102 103 private void addFoldingRegions(Set regions, List children) throws BadLocationException { 104 Iterator iter= children.iterator(); 106 while (iter.hasNext()) { 107 AntElementNode element = (AntElementNode) iter.next(); 108 if (element.getImportNode() != null || element.isExternal()) { 109 continue; } 111 int startLine= fDocument.getLineOfOffset(element.getOffset()); 112 int endLine= fDocument.getLineOfOffset(element.getOffset() + element.getLength()); 113 if (startLine < endLine) { 114 int start= fDocument.getLineOffset(startLine); 115 int end= fDocument.getLineOffset(endLine) + fDocument.getLineLength(endLine); 116 Position position= new Position(start, end - start); 117 regions.add(position); 118 fPositionToElement.put(position, element); 119 } 120 121 children= element.getChildNodes(); 122 if (children != null) { 123 addFoldingRegions(regions, children); 124 } 125 } 126 } 127 128 public void setDocument(IDocument document) { 129 fDocument= document; 130 } 131 } 132 | Popular Tags |