2 * Copyright 2000-2009 JetBrains s.r.o.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
16 package com
.intellij
.openapi
.vcs
.impl
;
18 import com
.intellij
.openapi
.editor
.Document
;
19 import com
.intellij
.openapi
.localVcs
.UpToDateLineNumberProvider
;
20 import com
.intellij
.openapi
.project
.Project
;
21 import com
.intellij
.openapi
.vcs
.ex
.LineStatusTracker
;
22 import com
.intellij
.openapi
.vcs
.ex
.Range
;
23 import com
.intellij
.openapi
.vfs
.VirtualFile
;
25 import java
.util
.List
;
30 public class UpToDateLineNumberProviderImpl
implements UpToDateLineNumberProvider
{
31 private final Document myDocument
;
32 private final Project myProject
;
33 private final String myUpToDateContent
;
34 private final VirtualFile myVf
;
36 public UpToDateLineNumberProviderImpl(Document document
, Project project
, String upToDateContent
, VirtualFile vf
) {
37 myDocument
= document
;
39 myUpToDateContent
= upToDateContent
;
43 public int getLineNumber(int currentNumber
) {
44 LineStatusTracker tracker
= LineStatusTrackerManager
.getInstance(myProject
).getLineStatusTracker(myDocument
);
45 if (tracker
== null) {
46 tracker
= LineStatusTrackerManager
.getInstance(myProject
).setUpToDateContent(myDocument
, myUpToDateContent
, myVf
);
48 return calcLineNumber(tracker
, currentNumber
);
51 private boolean endsWithSeparator(final CharSequence string
) {
52 if ((string
== null) || (string
.length() == 0)) {
55 final char latest
= string
.charAt(string
.length() - 1);
56 return ('\n' == latest
) || ('\r' == latest
);
59 // annotated content is not aware about latest line ends with end-line separator or not. ignore latest separator difference then
60 private String
fixLatestLineSeparator(final Document document
, final String content
) {
61 final CharSequence documentSequence
= document
.getCharsSequence();
62 if (endsWithSeparator(documentSequence
) && (! endsWithSeparator(content
))) {
63 int numCharsToCopy
= 1;
64 final int docLen
= documentSequence
.length();
66 final char beforeLatest
= documentSequence
.charAt(docLen
- 2);
67 if (('\r' == beforeLatest
) || ('\n' == beforeLatest
)) {
71 return content
+ documentSequence
.subSequence(docLen
- numCharsToCopy
, docLen
);
76 private static int calcLineNumber(LineStatusTracker tracker
, int currentNumber
){
77 if (tracker
== null) return -1;
78 List ranges
= tracker
.getRanges();
79 int result
= currentNumber
;
81 for (final Object range1
: ranges
) {
82 Range range
= (Range
)range1
;
83 int startOffset
= range
.getOffset1();
84 int endOffset
= range
.getOffset2();
86 if ((startOffset
<= currentNumber
) && (endOffset
> currentNumber
)) {
87 return ABSENT_LINE_NUMBER
;
90 if (endOffset
> currentNumber
) return result
;
92 int currentRangeLength
= endOffset
- startOffset
;
94 result
+= range
.getUpToDateRangeLength() - currentRangeLength
;