| /* |
| * Copyright 2000-2014 JetBrains s.r.o. |
| * |
| * Licensed under the Apache License, Version 2.0 (the "License"); |
| * you may not use this file except in compliance with the License. |
| * You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| |
| /* |
| * Created by IntelliJ IDEA. |
| * User: cdr |
| * Date: Aug 22, 2007 |
| * Time: 9:09:57 PM |
| */ |
| package com.intellij.injected.editor; |
| |
| import com.intellij.openapi.editor.Document; |
| import com.intellij.openapi.editor.event.DocumentEvent; |
| import com.intellij.openapi.editor.ex.RangeMarkerEx; |
| import com.intellij.openapi.util.Key; |
| import com.intellij.psi.PsiLanguageInjectionHost; |
| import org.jetbrains.annotations.NotNull; |
| |
| public class RangeMarkerWindow implements RangeMarkerEx { |
| |
| private final DocumentWindow myDocumentWindow; |
| private final RangeMarkerEx myHostMarker; |
| private final int myStartShift; |
| private final int myEndShift; |
| |
| /** |
| * Creates new <code>RangeMarkerWindow</code> object with the given data. |
| * |
| * @param documentWindow target document window |
| * @param hostMarker backing host range marker |
| * @param startShift there is a possible situation that injected fragment uses non-empty |
| * {@link PsiLanguageInjectionHost.Shred#getPrefix() prefix} and |
| * {@link PsiLanguageInjectionHost.Shred#getSuffix() suffix}. It's also possible that target |
| * injected offsets are located at prefix/suffix space. We need to hold additional information |
| * in order to perform {@code 'host -> injected'} mapping then. This argument specifies difference |
| * between the start offset of the given host range marker at the injected text and target injected text |
| * start offset |
| * @param endShift similar to the 'startShift' argument but specifies difference between the target injected host end offset |
| * and end offset of the given host range marker at the injected text |
| */ |
| public RangeMarkerWindow(@NotNull DocumentWindow documentWindow, RangeMarkerEx hostMarker, int startShift, int endShift) { |
| myDocumentWindow = documentWindow; |
| myHostMarker = hostMarker; |
| myStartShift = startShift; |
| myEndShift = endShift; |
| } |
| |
| @Override |
| @NotNull |
| public Document getDocument() { |
| return myDocumentWindow; |
| } |
| |
| @Override |
| public int getStartOffset() { |
| int hostOffset = myHostMarker.getStartOffset(); |
| return myDocumentWindow.hostToInjected(hostOffset) - myStartShift; |
| } |
| |
| @Override |
| public int getEndOffset() { |
| int hostOffset = myHostMarker.getEndOffset(); |
| return myDocumentWindow.hostToInjected(hostOffset) + myStartShift + myEndShift; |
| } |
| |
| @Override |
| public boolean isValid() { |
| if (!myHostMarker.isValid() || !myDocumentWindow.isValid()) return false; |
| int startOffset = getStartOffset(); |
| int endOffset = getEndOffset(); |
| return startOffset <= endOffset && endOffset <= myDocumentWindow.getTextLength(); |
| } |
| |
| @Override |
| public boolean setValid(boolean value) { |
| return myHostMarker.setValid(value); |
| } |
| |
| ////////////////////////////delegates |
| @Override |
| public void setGreedyToLeft(final boolean greedy) { |
| myHostMarker.setGreedyToLeft(greedy); |
| } |
| |
| @Override |
| public void setGreedyToRight(final boolean greedy) { |
| myHostMarker.setGreedyToRight(greedy); |
| } |
| |
| @Override |
| public <T> T getUserData(@NotNull final Key<T> key) { |
| return myHostMarker.getUserData(key); |
| } |
| |
| @Override |
| public <T> void putUserData(@NotNull final Key<T> key, final T value) { |
| myHostMarker.putUserData(key, value); |
| } |
| |
| @Override |
| public void documentChanged(final DocumentEvent e) { |
| myHostMarker.documentChanged(e); |
| } |
| @Override |
| public long getId() { |
| return myHostMarker.getId(); |
| } |
| |
| public RangeMarkerEx getDelegate() { |
| return myHostMarker; |
| } |
| |
| @Override |
| public boolean isGreedyToRight() { |
| return myHostMarker.isGreedyToRight(); |
| } |
| |
| @Override |
| public boolean isGreedyToLeft() { |
| return myHostMarker.isGreedyToLeft(); |
| } |
| |
| @Override |
| public int intervalStart() { |
| return getStartOffset(); |
| } |
| |
| @Override |
| public int intervalEnd() { |
| return getEndOffset(); |
| } |
| |
| @Override |
| public int setIntervalStart(int start) { |
| throw new IllegalStateException(); |
| } |
| |
| @Override |
| public int setIntervalEnd(int end) { |
| throw new IllegalStateException(); |
| } |
| |
| @Override |
| public void dispose() { |
| myHostMarker.dispose(); |
| } |
| |
| @Override |
| public String toString() { |
| return "RangeMarkerWindow" + (isGreedyToLeft() ? "[" : "(") + (isValid() ? "valid" : "invalid") + "," + |
| getStartOffset() + "," + getEndOffset() + |
| (isGreedyToRight() ? "]" : ")") + " " + getId(); |
| } |
| } |