Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Use of Tree line tracker in incremental mode #448

Merged
merged 2 commits into from
Jun 18, 2019
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -0,0 +1,150 @@
/*******************************************************************************
* Copyright (c) 2000, 2009 IBM Corporation and others.
*
* This program and the accompanying materials
* are made available under the terms of the Eclipse Public License 2.0
* which accompanies this distribution, and is available at
* https://www.eclipse.org/legal/epl-2.0/
*
* SPDX-License-Identifier: EPL-2.0
*
* Contributors:
* IBM Corporation - initial API and implementation
*******************************************************************************/
package org.eclipse.lsp4xml.commons;
//package org.eclipse.jface.text;

import org.eclipse.lsp4j.Position;

/**
* A line tracker maps character positions to line numbers and vice versa.
* Initially the line tracker is informed about its underlying text in order to
* initialize the mapping information. After that, the line tracker is informed
* about all changes of the underlying text allowing for incremental updates of
* the mapping information. It is the client's responsibility to actively inform
* the line tacker about text changes. For example, when using a line tracker in
* combination with a document the document controls the line tracker.
* <p>
* In order to provide backward compatibility for clients of <code>ILineTracker</code>, extension
* interfaces are used to provide a means of evolution. The following extension interfaces
* exist:
* <ul>
* <li> {@link org.eclipse.jface.text.ILineTrackerExtension} since version 3.1 introducing the concept
* of rewrite sessions.</li>
* </ul>
* <p>
* Clients may implement this interface or use the standard implementation
* </p>
* {@link org.eclipse.jface.text.DefaultLineTracker}or
* {@link org.eclipse.jface.text.ConfigurableLineTracker}.
*/
public interface ILineTracker {

/**
* Returns the line delimiter of the specified line. Returns <code>null</code> if the
* line is not closed with a line delimiter.
*
* @param line the line whose line delimiter is queried
* @return the line's delimiter or <code>null</code> if line does not have a delimiter
* @exception BadLocationException if the line number is invalid in this tracker's line structure
*/
String getLineDelimiter(int line) throws BadLocationException;

/**
* Computes the number of lines in the given text.
*
* @param text the text whose number of lines should be computed
* @return the number of lines in the given text
*/
int computeNumberOfLines(String text);

/**
* Returns the number of lines.
* <p>
* Note that a document always has at least one line.
* </p>
*
* @return the number of lines in this tracker's line structure
*/
int getNumberOfLines();

/**
* Returns the number of lines which are occupied by a given text range.
*
* @param offset the offset of the specified text range
* @param length the length of the specified text range
* @return the number of lines occupied by the specified range
* @exception BadLocationException if specified range is unknown to this tracker
*/
int getNumberOfLines(int offset, int length) throws BadLocationException;

/**
* Returns the position of the first character of the specified line.
*
* @param line the line of interest
* @return offset of the first character of the line
* @exception BadLocationException if the line is unknown to this tracker
*/
int getLineOffset(int line) throws BadLocationException;

/**
* Returns length of the specified line including the line's delimiter.
*
* @param line the line of interest
* @return the length of the line
* @exception BadLocationException if line is unknown to this tracker
*/
int getLineLength(int line) throws BadLocationException;

/**
* Returns the line number the character at the given offset belongs to.
*
* @param offset the offset whose line number to be determined
* @return the number of the line the offset is on
* @exception BadLocationException if the offset is invalid in this tracker
*/
int getLineNumberOfOffset(int offset) throws BadLocationException;

/**
* Returns a line description of the line at the given offset.
* The description contains the start offset and the length of the line
* excluding the line's delimiter.
*
* @param offset the offset whose line should be described
* @return a region describing the line
* @exception BadLocationException if offset is invalid in this tracker
*/
Line getLineInformationOfOffset(int offset) throws BadLocationException;

/**
* Returns a line description of the given line. The description
* contains the start offset and the length of the line excluding the line's
* delimiter.
*
* @param line the line that should be described
* @return a region describing the line
* @exception BadLocationException if line is unknown to this tracker
*/
Line getLineInformation(int line) throws BadLocationException;

/**
* Informs the line tracker about the specified change in the tracked text.
*
* @param offset the offset of the replaced text
* @param length the length of the replaced text
* @param text the substitution text
* @exception BadLocationException if specified range is unknown to this tracker
*/
void replace(int offset, int length, String text) throws BadLocationException;

/**
* Sets the tracked text to the specified text.
*
* @param text the new tracked text
*/
void set(String text);

Position getPositionAt(int position) throws BadLocationException;

int getOffsetAt(Position position) throws BadLocationException;
}
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@
*
* @since 3.2
*/
class ListLineTracker /* implements ILineTracker */ {
class ListLineTracker implements ILineTracker {

/** The predefined delimiters of this tracker */
public final static String[] DELIMITERS = { "\r", "\n", "\r\n" }; //$NON-NLS-3$ //$NON-NLS-1$ //$NON-NLS-2$
Expand Down Expand Up @@ -104,6 +104,7 @@ private int findLine(int offset) {
return left;
}

@Override
public final Position getPositionAt(int offset) throws BadLocationException {
int lineNumber = getLineNumberOfOffset(offset);
int lines = fLines.size();
Expand All @@ -120,7 +121,53 @@ public final Position getPositionAt(int offset) throws BadLocationException {
return new Position(lineNumber, character);
}

private final int getLineNumberOfOffset(int position) throws BadLocationException {

/**
* Returns the number of lines covered by the specified text range.
*
* @param startLine the line where the text range starts
* @param offset the start offset of the text range
* @param length the length of the text range
* @return the number of lines covered by this text range
* @exception BadLocationException if range is undefined in this tracker
*/
private int getNumberOfLines(int startLine, int offset, int length) throws BadLocationException {

if (length == 0)
return 1;

int target= offset + length;

Line l= fLines.get(startLine);

if (l.delimiter == null)
return 1;

if (l.offset + l.length > target)
return 1;

if (l.offset + l.length == target)
return 2;

return getLineNumberOfOffset(target) - startLine + 1;
}

@Override
public final int getLineLength(int line) throws BadLocationException {
int lines= fLines.size();

if (line < 0 || line > lines)
throw new BadLocationException();

if (lines == 0 || lines == line)
return 0;

Line l= fLines.get(line);
return l.length;
}

@Override
public final int getLineNumberOfOffset(int position) throws BadLocationException {
if (position < 0) {
throw new BadLocationException("Negative offset : " + position); //$NON-NLS-1$
} else if (position > fTextLength) {
Expand All @@ -140,6 +187,7 @@ private final int getLineNumberOfOffset(int position) throws BadLocationExceptio
return findLine(position);
}

@Override
public int getOffsetAt(Position position) throws BadLocationException {
int line = position.getLine();
int lines = fLines.size();
Expand Down Expand Up @@ -172,6 +220,23 @@ public int getOffsetAt(Position position) throws BadLocationException {
return offset;
}

@Override
public final Line getLineInformationOfOffset(int position) throws BadLocationException {
if (position > fTextLength)
throw new BadLocationException("Offset > length: " + position + " > " + fTextLength); //$NON-NLS-1$//$NON-NLS-2$

if (position == fTextLength) {
int size= fLines.size();
if (size == 0)
return new Line(0, 0);
Line l= fLines.get(size - 1);
return (l.delimiter != null ? new Line(fTextLength, 0) : new Line(fTextLength - l.length, l.length));
}

return getLineInformation(findLine(position));
}

@Override
public final Line getLineInformation(int line) throws BadLocationException {
int lines = fLines.size();

Expand All @@ -190,7 +255,7 @@ public final Line getLineInformation(int line) throws BadLocationException {
return (l.delimiter != null ? new Line(l.offset, l.length - l.delimiter.length()) : l);
}

// @Override
@Override
public final int getLineOffset(int line) throws BadLocationException {
int lines = fLines.size();

Expand All @@ -211,7 +276,7 @@ public final int getLineOffset(int line) throws BadLocationException {
return l.offset;
}

// @Override
@Override
public final int getNumberOfLines() {
int lines = fLines.size();

Expand All @@ -221,26 +286,31 @@ public final int getNumberOfLines() {
Line l = fLines.get(lines - 1);
return (l.delimiter != null ? lines + 1 : lines);
}

@Override
public final int getNumberOfLines(int position, int length) throws BadLocationException {

/*
* @Override public final int getNumberOfLines(int position, int length) throws
* BadLocationException {
*
* if (position < 0 || position + length > fTextLength) throw new
* BadLocationException();
*
* if (length == 0) // optimization return 1;
*
* return getNumberOfLines(getLineNumberOfOffset(position), position, length); }
*/
if (position < 0 || position + length > fTextLength)
throw new BadLocationException();

/*
* @Override public final int computeNumberOfLines(String text) { int count= 0;
* int start= 0; DelimiterInfo delimiterInfo= nextDelimiterInfo(text, start);
* while (delimiterInfo != null && delimiterInfo.delimiterIndex > -1) { ++count;
* start= delimiterInfo.delimiterIndex + delimiterInfo.delimiterLength;
* delimiterInfo= nextDelimiterInfo(text, start); } return count; }
*/
if (length == 0) // optimization
return 1;

return getNumberOfLines(getLineNumberOfOffset(position), position, length);
}

@Override
public final int computeNumberOfLines(String text) {
int count= 0;
int start= 0;
DelimiterInfo delimiterInfo= nextDelimiterInfo(text, start);
while (delimiterInfo != null && delimiterInfo.delimiterIndex > -1) {
++count;
start= delimiterInfo.delimiterIndex + delimiterInfo.delimiterLength;
delimiterInfo= nextDelimiterInfo(text, start);
}
return count;
}

public final String getLineDelimiter(int line) throws BadLocationException {
int lines = fLines.size();
Expand Down Expand Up @@ -348,7 +418,12 @@ private int createLines(String text, int insertPosition, int offset) {
return count;
}

// @Override
@Override
public final void replace(int position, int length, String text) throws BadLocationException {
throw new UnsupportedOperationException();
}

@Override
public final void set(String text) {
fLines.clear();
if (text != null) {
Expand Down
Loading