Index: src/org/openide/text/CloneableEditorSupport.java =================================================================== RCS file: /cvs/openide/src/org/openide/text/CloneableEditorSupport.java,v retrieving revision 1.48.2.2 diff -u -r1.48.2.2 CloneableEditorSupport.java --- src/org/openide/text/CloneableEditorSupport.java 10 Jan 2002 12:19:14 -0000 1.48.2.2 +++ src/org/openide/text/CloneableEditorSupport.java 20 Mar 2002 14:40:14 -0000 @@ -143,6 +143,8 @@ /** lines set for this object */ private Line.Set lineSet; + /** Lock used when for updating lineSet. */ + private final Object LOCK_LINE_SET = new Object(); /** position manager */ private PositionRef.Manager positionManager; @@ -958,17 +960,27 @@ * @return the set */ Line.Set updateLineSet (boolean clear) { - if (lineSet != null && !clear) { - return lineSet; - } + synchronized(LOCK_LINE_SET) { + if(lineSet != null && !clear) { + return lineSet; + } - if (doc == null) { - lineSet = new EditorSupportLineSet.Closed (CloneableEditorSupport.this); - } else { - lineSet = new EditorSupportLineSet (CloneableEditorSupport.this, doc); - } + Line.Set oldSet = lineSet; + + if (doc == null) { + lineSet = new EditorSupportLineSet.Closed(CloneableEditorSupport.this); + } else { + lineSet = new EditorSupportLineSet(CloneableEditorSupport.this, doc); + } - return lineSet; + if(oldSet != null) { + synchronized(oldSet.lines) { + lineSet.lines.putAll(oldSet.lines); + } + } + + return lineSet; + } } Index: src/org/openide/text/DocumentLine.java =================================================================== RCS file: /cvs/openide/src/org/openide/text/DocumentLine.java,v retrieving revision 1.40.2.1 diff -u -r1.40.2.1 DocumentLine.java --- src/org/openide/text/DocumentLine.java 11 Dec 2001 14:56:04 -0000 1.40.2.1 +++ src/org/openide/text/DocumentLine.java 20 Mar 2002 14:40:14 -0000 @@ -14,8 +14,9 @@ package org.openide.text; import java.io.*; -import java.util.*; -import java.lang.ref.*; +import java.util.ArrayList; +import java.util.Iterator; +import java.util.List; import java.util.WeakHashMap; import javax.swing.text.*; import javax.swing.event.*; @@ -23,6 +24,7 @@ import org.openide.*; import org.openide.loaders.*; +import org.openide.util.WeakSet; import org.openide.util.WeakListener; import org.openide.util.Task; import org.openide.util.RequestProcessor; @@ -80,7 +82,7 @@ /** Init listeners */ - private void init () { + void init () { listener = new LR (); pos.getCloneableEditorSupport ().addChangeListener (WeakListener.change (listener, pos.getCloneableEditorSupport ())); } @@ -272,7 +274,9 @@ /** Register line. */ Object readResolve() throws ObjectStreamException { - return Set.registerLine (this); +// return Set.registerLine (this); + //Set.registerPendingLine(this); + return this.pos.getCloneableEditorSupport().getLineSet().registerLine(this); } @@ -623,12 +627,11 @@ */ public static abstract class Set extends Line.Set { /** listener on document changes */ - private LineListener listener; + private final LineListener listener; /** all lines in the set or null */ private java.util.List list; - /** map to hold all existing lines (Line, Reference (Line)) */ - private static WeakHashMap allLines = new WeakHashMap (37); + /** Constructor. * @param doc document to work on */ @@ -640,52 +643,61 @@ listener = new LineListener (doc, support); } + /** Find the line given as parameter in list of all lines attached to this set * and if the line exist in the list, notify it about being edited. */ - boolean fireLineChanged(Line comparingLine, DocumentEvent p0) { - Reference ref = (Reference)allLines.get (comparingLine); - if (ref == null) { - return false; - } - Line line = (Line)ref.get (); + void linesChanged(int startLineNumber, int endLineNumber, DocumentEvent p0) { + List changedLines = getLinesFromRange(startLineNumber, endLineNumber); - if(line == null) { - return false; + for(Iterator it = changedLines.iterator(); it.hasNext(); ) { + Line line = (Line)it.next(); + + line.firePropertyChange(Annotatable.PROP_TEXT, null, null); + + // revalidate all parts attached to this line + // that they are still part of the line + if(line instanceof DocumentLine) { + ((DocumentLine)line).notifyChange(p0, this, listener.doc); + } } - - line.firePropertyChange(Annotatable.PROP_TEXT, null, null); - - // revalidate all parts attached to this line - // that they are still part of the line - if (line instanceof DocumentLine) - ((DocumentLine)line).notifyChange(p0, this, listener.doc); - - return true; } /** Find the line given as parameter in list of all lines attached to this set * and if the line exist in the list, notify it about being moved. */ - boolean fireLineMoved(Line comparingLine) { - Reference ref = (Reference)allLines.get (comparingLine); - if (ref == null) { - return false; - } - Line line = (Line)ref.get (); + void linesMoved(int startLineNumber, int endLineNumber) { + List movedLines = getLinesFromRange(startLineNumber, endLineNumber); - if(line == null) { - return false; + for(Iterator it = movedLines.iterator(); it.hasNext(); ) { + Line line = (Line)it.next(); + line.firePropertyChange(Line.PROP_LINE_NUMBER, null, null); + + // notify all parts attached to this line + // that they were moved + if (line instanceof DocumentLine) { + ((DocumentLine)line).notifyMove(); + } } - - line.firePropertyChange(Line.PROP_LINE_NUMBER, null, null); - - // notify all parts attached to this line - // that they were moved - if (line instanceof DocumentLine) - ((DocumentLine)line).notifyMove(); - - return true; } + /** Gets the lines with line number whitin the range inclusive. + * @return List of lines from range inclusive */ + private List getLinesFromRange(int startLineNumber, int endLineNumber) { + List linesInRange = new ArrayList(10); + + synchronized(lines) { + for(Iterator it = lines.keySet().iterator(); it.hasNext(); ) { + Line line = (Line)it.next(); + int lineNumber = line.getLineNumber(); + if(startLineNumber <= lineNumber + && lineNumber <= endLineNumber) { + linesInRange.add(line); + } + } + } + + return linesInRange; + } + /* Returns an unmodifiable set of Lines sorted by their * line numbers that contains all lines holded by this * Line.Set. @@ -714,10 +726,8 @@ public Line getOriginal (int line) throws IndexOutOfBoundsException { int newLine = listener.getLine (line); int offset = NbDocument.findLineOffset (listener.doc, newLine); - // System.out.println("Then: " + line + " now: " + newLine + " offset: " + offset); // NOI18N - Line ll = registerLine (createLine (offset)); - return ll; + return this.registerLine(createLine(offset)); } /* Creates current line. @@ -727,10 +737,8 @@ */ public Line getCurrent (int line) throws IndexOutOfBoundsException { int offset = NbDocument.findLineOffset (listener.doc, line); - // System.out.println("Then: " + line + " now: " + newLine + " offset: " + offset); // NOI18N - Line ll = registerLine (createLine (offset)); - return ll; + return this.registerLine(createLine(offset)); } /** Creates a {@link Line} for a given offset. @@ -739,24 +747,6 @@ */ protected abstract Line createLine (int offset); - /** Registers the line. - * @param l line to register - * @return the line l or line previously registered - */ - static synchronized Line registerLine (Line l) { - Reference ref = (Reference)allLines.get (l); - Line prev = ref == null ? null : (Line)ref.get (); - if (prev == null) { - if (l instanceof DocumentLine) - ((DocumentLine)l).init (); - allLines.put (l, new WeakReference (l)); - return l; - } else { - return prev; - } - - - } } Index: src/org/openide/text/EditorSupportLineSet.java =================================================================== RCS file: /cvs/openide/src/org/openide/text/EditorSupportLineSet.java,v retrieving revision 1.27.14.1 diff -u -r1.27.14.1 EditorSupportLineSet.java --- src/org/openide/text/EditorSupportLineSet.java 14 Dec 2001 15:10:45 -0000 1.27.14.1 +++ src/org/openide/text/EditorSupportLineSet.java 20 Mar 2002 14:40:14 -0000 @@ -125,7 +125,7 @@ */ public java.util.List getLines () { if (delegate != null) { - return delegate.getLines (); + return delegate.getLines(); } // PENDING return new java.util.ArrayList (); @@ -159,8 +159,7 @@ // obj can be null, sorry... DataObject obj = support.getDataObjectHack (); - Line l = registerLine (new SupportLine (obj, ref, support)); - return l; + return this.registerLine(new SupportLine(obj, ref, support)); } Index: src/org/openide/text/Line.java =================================================================== RCS file: /cvs/openide/src/org/openide/text/Line.java,v retrieving revision 1.16.14.1 diff -u -r1.16.14.1 Line.java --- src/org/openide/text/Line.java 3 Dec 2001 12:37:27 -0000 1.16.14.1 +++ src/org/openide/text/Line.java 20 Mar 2002 14:40:14 -0000 @@ -14,7 +14,11 @@ package org.openide.text; import java.io.*; +import java.lang.ref.Reference; +import java.lang.ref.WeakReference; import java.util.Date; +import java.util.Map; +import java.util.WeakHashMap; import org.openide.filesystems.FileObject; import org.openide.loaders.DataObject; @@ -258,6 +262,16 @@ /** date when the object has been created */ private Date date; + /** Map which contains all lines as keys and + * values weakReferences on itself. There woudl be better use + * set but there is missing get method, returning equal object. + * belonging to this Line.Set. + * @see DocumentLine#hashCode + * @see DocumentLine#equals + * @see #registerLine */ + final java.util.Map lines = new WeakHashMap(10); + + /** Create a new snapshot. Remembers the date when it was created. */ public Set () { date = new Date (); @@ -297,5 +311,28 @@ */ public abstract Line getCurrent (int line) throws IndexOutOfBoundsException; - } + /** Registers the line to this Line.Set. + * @param line Line to register + * @return registered Line. Note: the retruned + * Line could be different (identityHashCode not equal) + * from the one passed in */ + Line registerLine(Line line) { + synchronized(lines) { + Reference r = (Reference)lines.get(line); + Line in = (r != null ? (Line)r.get() : null); + + if(in == null) { + if(line instanceof DocumentLine) { + ((DocumentLine)line).init(); + } + + lines.put(line, new WeakReference(line)); + in = line; + } + + return in; + } + } + + } // End of class Line.Set. } Index: src/org/openide/text/LineListener.java =================================================================== RCS file: /cvs/openide/src/org/openide/text/LineListener.java,v retrieving revision 1.7.14.2 diff -u -r1.7.14.2 LineListener.java --- src/org/openide/text/LineListener.java 14 Dec 2001 15:10:45 -0000 1.7.14.2 +++ src/org/openide/text/LineListener.java 20 Mar 2002 14:40:14 -0000 @@ -35,12 +35,10 @@ private int lines; /** operations on lines */ private LineStruct struct; - /** "fake" line used only for comparing with other lines. Check how DocumentLine.equal() - * works. This line is used for comparing with lines in DocumentLine.Set.allLines array. This is - * more hack than regular solution */ - private ComparingLine comparingLine = null; + + /** Support necessary for getting Set of lines*/ - private CloneableEditorSupport support; + CloneableEditorSupport support; /** Creates new LineListener */ public LineListener (StyledDocument doc, CloneableEditorSupport support) { @@ -49,8 +47,6 @@ root = NbDocument.findLineRootElement (doc); orig = lines = root.getElementCount (); this.support = support; - if (support != null) - comparingLine = new ComparingLine(); doc.addDocumentListener(WeakListener.document (this, doc)); } @@ -83,16 +79,13 @@ Line.Set set = support.getLineSet (); if (!(set instanceof DocumentLine.Set)) return; - for (int i=lineNumber; i<=lineNumber+delta; i++) { - comparingLine.setLineNumber(i); - ((DocumentLine.Set)set).fireLineChanged(comparingLine, p0); - } + + // Notify lineSet there was changed range of lines. + ((DocumentLine.Set)set).linesChanged(lineNumber, lineNumber+delta, p0); + if (delta > 0) { - // notify lines that there they were moved - for (int i=lineNumber; i 0) { - // notify lines that there they were moved - for (int i=lineNumber; i