Skip to main content
aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
Diffstat (limited to 'bundles/org.eclipse.compare/compare/org/eclipse/compare/internal/DocLineComparator.java')
-rw-r--r--bundles/org.eclipse.compare/compare/org/eclipse/compare/internal/DocLineComparator.java216
1 files changed, 216 insertions, 0 deletions
diff --git a/bundles/org.eclipse.compare/compare/org/eclipse/compare/internal/DocLineComparator.java b/bundles/org.eclipse.compare/compare/org/eclipse/compare/internal/DocLineComparator.java
new file mode 100644
index 000000000..81591752b
--- /dev/null
+++ b/bundles/org.eclipse.compare/compare/org/eclipse/compare/internal/DocLineComparator.java
@@ -0,0 +1,216 @@
+/*
+ * Licensed Materials - Property of IBM,
+ * WebSphere Studio Workbench
+ * (c) Copyright IBM Corp 2000, 2001
+ */
+package org.eclipse.compare.internal;
+
+import org.eclipse.swt.SWTError;
+import org.eclipse.jface.text.*;
+import org.eclipse.compare.rangedifferencer.IRangeComparator;
+import org.eclipse.compare.contentmergeviewer.ITokenComparator;
+
+/**
+ * Implements the <code>ITokenComparator</code> interface for lines in a document.
+ * A <code>DocLineComparator</code> is used as the input for the <code>RangeDifferencer</code>
+ * engine to perform a line oriented compare on documents.
+ * <p>
+ * A <code>DocLineComparator</code> doesn't know anything about line separators because
+ * its notion of lines is solely defined in the underlying <code>IDocument</code>.
+ */
+public class DocLineComparator implements IRangeComparator {
+
+ private IDocument fDocument;
+ private int fLineOffset;
+ private int fLineCount;
+ private int fLength;
+ private boolean fIgnoreWhiteSpace;
+
+ /**
+ * Creates a <code>DocLineComparator</code> for the given document range.
+ * ignoreWhiteSpace controls whether comparing lines (in method
+ * <code>rangesEqual<code>) should ignore whitespace.
+ *
+ * @param document the document from which the lines are taken
+ * @param region if non-<code>null</code> only lines within this range are taken
+ * @param ignoreWhiteSpace if <code>true</code> white space is ignored when comparing lines
+ */
+ public DocLineComparator(IDocument document, IRegion region, boolean ignoreWhiteSpace) {
+
+ fDocument= document;
+ fIgnoreWhiteSpace= ignoreWhiteSpace;
+
+ fLineOffset= 0;
+ if (region != null) {
+ fLength= region.getLength();
+ int start= region.getOffset();
+ try {
+ fLineOffset= fDocument.getLineOfOffset(start);
+ } catch (BadLocationException ex) {
+ }
+
+ if (fLength == 0)
+ fLineCount= 0;
+ else {
+ int endLine= fDocument.getNumberOfLines();
+ try {
+ endLine= fDocument.getLineOfOffset(start + fLength);
+ } catch (BadLocationException ex) {
+ }
+ fLineCount= endLine - fLineOffset + 1;
+ }
+
+ } else {
+ fLength= document.getLength();
+ fLineCount= fDocument.getNumberOfLines();
+ }
+ }
+
+ /**
+ * Returns the content of lines in the specified range as a String.
+ * This includes the line separators.
+ *
+ * @param start index of first line
+ * @param length number of lines
+ * @return the contents of the specified line range as a String
+ */
+ public String extract(int start, int length) {
+ if (fLength > 0) {
+ if (fLength == 1)
+ return extract(start);
+ int startPos= getTokenStart(start);
+ int endPos= getTokenStart(start + length);
+ try {
+ return fDocument.get(startPos, endPos - startPos);
+ } catch (BadLocationException e) {
+ System.out.println("extract("+fDocument.getLength()+"): " + startPos + " " + endPos);
+ }
+ }
+ return "";
+ }
+
+ /**
+ * Extract a single line from the underlying document without the line separator.
+ *
+ * @param line the number of the line to extract
+ * @return the contents of the line as a String
+ */
+ public String extract(int line) {
+ line += fLineOffset;
+ if (line < fLength) {
+ try {
+ IRegion r= fDocument.getLineInformation(line);
+ return fDocument.get(r.getOffset(), r.getLength());
+ // return fDocument.getLine(line);
+ } catch(BadLocationException e) {
+ }
+ }
+ return "";
+ }
+
+ /**
+ * Returns the number of lines in the document.
+ *
+ * @return number of lines
+ */
+ public int getRangeCount() {
+ return fLineCount;
+ }
+
+ /**
+ * Returns <code>true</code> if a line given by the first index
+ * matches a line specified by the other <code>IRangeComparator</code> and index.
+ *
+ * @param thisIndex the number of the line within this range comparator
+ * @param other the range comparator to compare this with
+ * @param otherIndex the number of the line within the other comparator
+ * @return <code>true</code> if the lines are equal
+ */
+ public boolean rangesEqual(int thisIndex, IRangeComparator other0, int otherIndex) {
+
+ if (other0 != null && other0.getClass() == getClass()) {
+ DocLineComparator other= (DocLineComparator) other0;
+
+ if (fIgnoreWhiteSpace) {
+ String s1= extract(thisIndex);
+ String s2= other.extract(otherIndex);
+ return compare(s1, s2);
+ }
+
+ int tlen= getTokenLength(thisIndex);
+ int olen= other.getTokenLength(otherIndex);
+ if (tlen == olen) {
+ String s1= extract(thisIndex);
+ String s2= other.extract(otherIndex);
+ return s1.equals(s2);
+ }
+ }
+ return false;
+ }
+
+ /* (non Javadoc)
+ * see IRangeComparator.skipRangeComparison
+ */
+ public boolean skipRangeComparison(int length, int max, IRangeComparator other) {
+ return false;
+ }
+
+ /* (non Javadoc)
+ * see ITokenComparator.getTokenStart
+ */
+ public int getTokenStart(int line) {
+ try {
+ IRegion r= fDocument.getLineInformation(fLineOffset + line);
+ return r.getOffset();
+ //return fDocument.getLineStartOffset(fLineOffset + line);
+ } catch (BadLocationException ex) {
+ return fDocument.getLength();
+ }
+ }
+
+ /* (non Javadoc)
+ * see ITokenComparator.getTokenEnd
+ */
+ public int getTokenEnd(int start, int length) {
+ return getTokenStart(start + length);
+ }
+
+ //---- private methods
+
+ private int getTokenLength(int line) {
+ if (fLength == 0)
+ return 0;
+ return getTokenStart(line + 1) - getTokenStart(line);
+ }
+
+ private boolean compare(String s1, String s2) {
+ int i1= 0;
+ int i2= 0;
+ int l1= s1.length();
+ int l2= s2.length();
+ char c1= ' ';
+ char c2= ' ';
+ while (i1 < l1 || i2 < l2) {
+ if (i1 < l1) {
+ c1= s1.charAt(i1);
+ if (Character.isWhitespace(c1)) {
+ i1++;
+ continue;
+ }
+ }
+ if (i2 < l2) {
+ c2= s2.charAt(i2);
+ if (Character.isWhitespace(c2)) {
+ i2++;
+ continue;
+ }
+ }
+ if (c1 != c2)
+ return false;
+ i1++;
+ i2++;
+ }
+ return true;
+ }
+}
+

Back to the top