blob: d4a63b0cf1d9cbcfce5b026dc03f4236ab6bcb78 [file] [log] [blame]
/*
* Copyright 2000-2009 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.
*/
package com.intellij.psi.util;
import com.intellij.openapi.util.TextRange;
import com.intellij.psi.ElementManipulators;
import com.intellij.psi.PsiElement;
import com.intellij.psi.PsiReference;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
/**
* @author Dmitry Avdeev
*/
public abstract class ReferenceSetBase<T extends PsiReference> {
public static final char DOT_SEPARATOR = '.';
private final List<T> myReferences;
private final PsiElement myElement;
private final char mySeparator;
public ReferenceSetBase(@NotNull PsiElement element) {
this(element, ElementManipulators.getOffsetInElement(element));
}
public ReferenceSetBase(@NotNull PsiElement element, int offset) {
this(ElementManipulators.getValueText(element), element, offset, DOT_SEPARATOR);
}
public ReferenceSetBase(final String text, @NotNull PsiElement element, int offset, final char separator) {
myElement = element;
mySeparator = separator;
myReferences = parse(text, offset);
}
public boolean isSoft() {
return true;
}
@NotNull
protected List<T> parse(String str, int offset) {
final List<T> references = new ArrayList<T>();
int current = -1;
int index = 0;
int next;
do {
next = findNextSeparator(str, current);
final TextRange range = new TextRange(offset + current + 1, offset + (next >= 0 ? next : str.length()));
references.addAll(createReferences(range, index ++));
} while ((current = next) >= 0);
return references;
}
protected int findNextSeparator(final String str, final int current) {
final int next;
next = str.indexOf(mySeparator, current + 1);
return next;
}
@Nullable
protected T createReference(final TextRange range, final int index) {
return null;
}
protected List<T> createReferences(final TextRange range, final int index) {
T reference = createReference(range, index);
return reference == null? Collections.<T>emptyList() : Collections.singletonList(reference);
}
public PsiElement getElement() {
return myElement;
}
public List<T> getReferences() {
return myReferences;
}
public PsiReference[] getPsiReferences() {
return myReferences.toArray(new PsiReference[myReferences.size()]);
}
public T getReference(int index) {
return myReferences.get(index);
}
@Nullable
public T getLastReference() {
return myReferences.isEmpty() ? null : getReference(myReferences.size() - 1);
}
}