下面列出了com.intellij.psi.impl.source.tree.ChangeUtil#com.intellij.psi.impl.source.codeStyle.CodeEditUtil 实例代码,或者点击链接到github查看源代码,也可以在右侧发表评论。
@Override
@Nonnull
public PsiFile createFileFromText(@Nonnull String name,
@Nonnull FileType fileType,
@Nonnull CharSequence text,
long modificationStamp,
final boolean physical,
boolean markAsCopy) {
final LightVirtualFile virtualFile = new LightVirtualFile(name, fileType, text, modificationStamp);
if (fileType instanceof LanguageFileType) {
final Language language =
LanguageSubstitutors.INSTANCE.substituteLanguage(((LanguageFileType)fileType).getLanguage(), virtualFile, myManager.getProject());
final PsiFile file = trySetupPsiForFile(virtualFile, language, LanguageVersionUtil.findDefaultVersion(language), physical, markAsCopy);
if (file != null) return file;
}
final SingleRootFileViewProvider singleRootFileViewProvider = new SingleRootFileViewProvider(myManager, virtualFile, physical);
final PsiPlainTextFileImpl plainTextFile = new PsiPlainTextFileImpl(singleRootFileViewProvider);
if (markAsCopy) CodeEditUtil.setNodeGenerated(plainTextFile.getNode(), true);
return plainTextFile;
}
private static void handleReformatMarkers(@Nonnull final FileViewProvider key, @Nonnull final Set<? super PostprocessFormattingTask> rangesToProcess) {
final Document document = key.getDocument();
if (document == null) {
return;
}
for (final FileElement fileElement : ((AbstractFileViewProvider)key).getKnownTreeRoots()) {
fileElement.acceptTree(new RecursiveTreeElementWalkingVisitor() {
@Override
protected void visitNode(TreeElement element) {
if (CodeEditUtil.isMarkedToReformatBefore(element)) {
CodeEditUtil.markToReformatBefore(element, false);
rangesToProcess.add(new ReformatWithHeadingWhitespaceTask(document.createRangeMarker(element.getStartOffset(), element.getStartOffset())));
}
else if (CodeEditUtil.isMarkedToReformat(element)) {
CodeEditUtil.markToReformat(element, false);
rangesToProcess.add(new ReformatWithHeadingWhitespaceTask(document.createRangeMarker(element.getStartOffset(), element.getStartOffset() + element.getTextLength())));
}
super.visitNode(element);
}
});
}
}
/**
* This method is used in order to add elements to the back of a map,
* it is derived from {@link ASTDelegatePsiElement#addInternal(ASTNode, ASTNode, ASTNode, Boolean)}.
*/
private static PsiElement realAddBefore(@NotNull GrListOrMap element, @NotNull PsiElement newElement, @NotNull PsiElement anchor) {
CheckUtil.checkWritable(element);
TreeElement elementCopy = ChangeUtil.copyToElement(newElement);
ASTNode anchorNode = getAnchorNode(element, anchor.getNode(), true);
ASTNode newNode = CodeEditUtil.addChildren(element.getNode(), elementCopy, elementCopy, anchorNode);
if (newNode == null) {
throw new IncorrectOperationException("Element cannot be added");
}
if (newNode instanceof TreeElement) {
return ChangeUtil.decodeInformation((TreeElement)newNode).getPsi();
}
return newNode.getPsi();
}
@Override
@RequiredUIAccess
public void invoke(@Nonnull Project project, Editor editor, PsiFile file) throws IncorrectOperationException
{
DotNetVariable element = myVariablePointer.getElement();
if(element == null)
{
return;
}
PsiDocumentManager.getInstance(project).commitAllDocuments();
String defaultValueForType = MethodGenerateUtil.getDefaultValueForType(element.toTypeRef(false), element);
if(defaultValueForType == null)
{
return;
}
DotNetExpression expression = CSharpFileFactory.createExpression(project, defaultValueForType);
PsiElement nameIdentifier = element.getNameIdentifier();
if(nameIdentifier == null)
{
return;
}
ASTNode variableNode = element.getNode();
ASTNode semicolon = variableNode.findChildByType(CSharpTokens.SEMICOLON);
variableNode.addLeaf(CSharpTokens.WHITE_SPACE, " ", semicolon);
variableNode.addLeaf(CSharpTokens.EQ, "=", semicolon);
variableNode.addLeaf(CSharpTokens.WHITE_SPACE, " ", semicolon);
ASTNode node = expression.getNode();
CodeEditUtil.setOldIndentation((TreeElement) node, 0);
variableNode.addChild(node, semicolon);
editor.getCaretModel().moveToOffset(element.getTextRange().getEndOffset());
}
@Override
public void deleteChildRange(final PsiElement first, final PsiElement last) throws IncorrectOperationException {
CheckUtil.checkWritable(this);
ASTNode firstElement = SourceTreeToPsiMap.psiElementToTree(first);
ASTNode lastElement = SourceTreeToPsiMap.psiElementToTree(last);
LOG.assertTrue(firstElement.getTreeParent() == getNode());
LOG.assertTrue(lastElement.getTreeParent() == getNode());
CodeEditUtil.removeChildren(getNode(), firstElement, lastElement);
}
@Override
public PsiElement replace(@Nonnull final PsiElement newElement) throws IncorrectOperationException {
CheckUtil.checkWritable(this);
TreeElement elementCopy = ChangeUtil.copyToElement(newElement);
if (getParent() instanceof ASTDelegatePsiElement) {
final ASTDelegatePsiElement parentElement = (ASTDelegatePsiElement)getParent();
parentElement.replaceChildInternal(this, elementCopy);
}
else {
CodeEditUtil.replaceChild(getParent().getNode(), getNode(), elementCopy);
}
elementCopy = ChangeUtil.decodeInformation(elementCopy);
return SourceTreeToPsiMap.treeElementToPsi(elementCopy);
}
@Nonnull
public static LeafElement createSingleLeafElement(@Nonnull IElementType type, CharSequence buffer, int startOffset, int endOffset, CharTable table, PsiManager manager, PsiFile originalFile) {
DummyHolder dummyHolder = DummyHolderFactory.createHolder(manager, table, type.getLanguage());
dummyHolder.setOriginalFile(originalFile);
FileElement holderElement = dummyHolder.getTreeElement();
LeafElement newElement = ASTFactory.leaf(type, holderElement.getCharTable().intern(
buffer, startOffset, endOffset));
holderElement.rawAddChildren(newElement);
CodeEditUtil.setNodeGenerated(newElement, true);
return newElement;
}
@Nonnull
public static LeafElement createSingleLeafElement(@Nonnull IElementType type, CharSequence buffer, int startOffset, int endOffset, CharTable table, PsiManager manager, boolean generatedFlag) {
final FileElement holderElement = DummyHolderFactory.createHolder(manager, table, type.getLanguage()).getTreeElement();
final LeafElement newElement = ASTFactory.leaf(type, holderElement.getCharTable().intern(
buffer, startOffset, endOffset));
holderElement.rawAddChildren(newElement);
if(generatedFlag) CodeEditUtil.setNodeGenerated(newElement, true);
return newElement;
}
/**
* @return First element that was appended (for example whitespaces could be skipped)
*/
public TreeElement addInternal(TreeElement first, ASTNode last, @Nullable ASTNode anchor, @Nullable Boolean before) {
ASTNode anchorBefore;
if (anchor == null) {
anchorBefore = before == null || before.booleanValue() ? null : getFirstChildNode();
}
else {
anchorBefore = before.booleanValue() ? anchor : anchor.getTreeNext();
}
return (TreeElement)CodeEditUtil.addChildren(this, first, last, anchorBefore);
}
@Override
public void addLeaf(@Nonnull final IElementType leafType, @Nonnull CharSequence leafText, final ASTNode anchorBefore) {
FileElement holder = new DummyHolder(getManager(), null).getTreeElement();
final LeafElement leaf = ASTFactory.leaf(leafType, holder.getCharTable().intern(leafText));
CodeEditUtil.setNodeGenerated(leaf, true);
holder.rawAddChildren(leaf);
addChild(leaf, anchorBefore);
}
public static PsiElement addRange(PsiElement thisElement,
PsiElement first,
PsiElement last,
ASTNode anchor,
Boolean before) throws IncorrectOperationException {
CheckUtil.checkWritable(thisElement);
final CharTable table = findCharTableByTree(SourceTreeToPsiMap.psiElementToTree(thisElement));
TreeElement copyFirst = null;
ASTNode copyLast = null;
ASTNode next = SourceTreeToPsiMap.psiElementToTree(last).getTreeNext();
ASTNode parent = null;
for (ASTNode element = SourceTreeToPsiMap.psiElementToTree(first); element != next; element = element.getTreeNext()) {
TreeElement elementCopy = ChangeUtil.copyElement((TreeElement)element, table);
if (element == first.getNode()) {
copyFirst = elementCopy;
}
if (element == last.getNode()) {
copyLast = elementCopy;
}
if (parent == null) {
parent = elementCopy.getTreeParent();
}
else {
if(elementCopy.getElementType() == TokenType.WHITE_SPACE)
CodeEditUtil.setNodeGenerated(elementCopy, true);
parent.addChild(elementCopy, null);
}
}
if (copyFirst == null) return null;
copyFirst = ((CompositeElement)SourceTreeToPsiMap.psiElementToTree(thisElement)).addInternal(copyFirst, copyLast, anchor, before);
for (TreeElement element = copyFirst; element != null; element = element.getTreeNext()) {
element = ChangeUtil.decodeInformation(element);
if (element.getTreePrev() == null) {
copyFirst = element;
}
}
return SourceTreeToPsiMap.treeElementToPsi(copyFirst);
}
@Override
public void deleteChildRange(PsiElement first, PsiElement last) throws IncorrectOperationException {
CheckUtil.checkWritable(this);
ASTNode firstElement = SourceTreeToPsiMap.psiElementToTree(first);
ASTNode lastElement = SourceTreeToPsiMap.psiElementToTree(last);
LOG.assertTrue(firstElement.getTreeParent() == this);
LOG.assertTrue(lastElement.getTreeParent() == this);
CodeEditUtil.removeChildren(this, firstElement, lastElement);
}
@Override
public void deleteChildRange(PsiElement first, PsiElement last) throws IncorrectOperationException {
CheckUtil.checkWritable(this);
ASTNode firstElement = first.getNode();
ASTNode lastElement = last.getNode();
LOG.assertTrue(firstElement.getTreeParent() == this);
LOG.assertTrue(lastElement.getTreeParent() == this);
CodeEditUtil.removeChildren(this, firstElement, lastElement);
}
private static void saveIndentationToCopy(final TreeElement original, final TreeElement element) {
if(original == null || element == null || CodeEditUtil.isNodeGenerated(original)) return;
final int indentation = CodeEditUtil.getOldIndentation(original);
if(indentation < 0) CodeEditUtil.saveWhitespacesInfo(original);
CodeEditUtil.setOldIndentation(element, CodeEditUtil.getOldIndentation(original));
if(indentation < 0) CodeEditUtil.setOldIndentation(original, -1);
}
@Override
public void deleteChildRange(PsiElement first, PsiElement last) throws IncorrectOperationException {
CheckUtil.checkWritable(this);
if (first == null) {
LOG.assertTrue(last == null);
return;
}
ASTNode firstElement = SourceTreeToPsiMap.psiElementToTree(first);
ASTNode lastElement = SourceTreeToPsiMap.psiElementToTree(last);
CompositeElement treeElement = calcTreeElement();
LOG.assertTrue(firstElement.getTreeParent() == treeElement);
LOG.assertTrue(lastElement.getTreeParent() == treeElement);
CodeEditUtil.removeChildren(treeElement, firstElement, lastElement);
}
@Nonnull
public PsiFile createFileFromText(@Nonnull String name,
@Nonnull FileType fileType,
final Language language,
@Nonnull Language targetLanguage,
@Nonnull CharSequence text,
long modificationStamp,
final boolean physical,
boolean markAsCopy) {
final LightVirtualFile virtualFile = new LightVirtualFile(name, fileType, text, modificationStamp);
final ParserDefinition parserDefinition = LanguageParserDefinitions.INSTANCE.forLanguage(language);
final FileViewProviderFactory factory = LanguageFileViewProviders.INSTANCE.forLanguage(language);
FileViewProvider viewProvider = factory != null ? factory.createFileViewProvider(virtualFile, language, myManager, physical) : null;
if (viewProvider == null) viewProvider = new SingleRootFileViewProvider(myManager, virtualFile, physical);
if (parserDefinition != null) {
final PsiFile psiFile = viewProvider.getPsi(targetLanguage);
if (psiFile != null) {
if (markAsCopy) {
markGenerated(psiFile);
}
return psiFile;
}
}
final SingleRootFileViewProvider singleRootFileViewProvider = new SingleRootFileViewProvider(myManager, virtualFile, physical);
final PsiPlainTextFileImpl plainTextFile = new PsiPlainTextFileImpl(singleRootFileViewProvider);
if (markAsCopy) CodeEditUtil.setNodeGenerated(plainTextFile.getNode(), true);
return plainTextFile;
}
@Override
public void commitChanges() {
CodeEditUtil.allowToMarkNodesForPostponedFormatting(false);
try {
PsiDocumentManager.getInstance(myProject).commitDocument(myDocument);
}
finally {
CodeEditUtil.allowToMarkNodesForPostponedFormatting(true);
}
}
private void postponeFormatting(@Nonnull FileViewProvider viewProvider, @Nonnull ASTNode child) {
if (!CodeEditUtil.isNodeGenerated(child) && child.getElementType() != TokenType.WHITE_SPACE) {
final int oldIndent = CodeEditUtil.getOldIndentation(child);
LOG.assertTrue(oldIndent >= 0, "for not generated items old indentation must be defined: element=" + child + ", text=" + child.getText());
}
List<ASTNode> list = getContext().myReformatElements.get(viewProvider);
if (list == null) {
list = new ArrayList<>();
getContext().myReformatElements.put(viewProvider, list);
if (Holder.STORE_REFORMAT_ORIGINATOR_STACKTRACE) {
viewProvider.putUserData(REFORMAT_ORIGINATOR, new Throwable());
}
}
list.add(child);
}
@RequiredReadAction
public ASTNode addInternal(ASTNode first, ASTNode last, ASTNode anchor, Boolean before) {
return CodeEditUtil.addChildren(getNode(), first, last, getAnchorNode(anchor, before));
}
public void deleteChildInternal(@Nonnull ASTNode child) {
CodeEditUtil.removeChild(getNode(), child);
}
public void replaceChildInternal(final PsiElement child, final TreeElement newElement) {
CodeEditUtil.replaceChild(getNode(), child.getNode(), newElement);
}
@Nonnull
public static LeafElement whitespace(final CharSequence text) {
final PsiWhiteSpaceImpl w = new PsiWhiteSpaceImpl(WHITESPACES.intern(text));
CodeEditUtil.setNodeGenerated(w, true);
return w;
}
public void deleteChildInternal(@Nonnull ASTNode child) {
CodeEditUtil.removeChild(this, child);
}
public void replaceChildInternal(@Nonnull ASTNode child, @Nonnull TreeElement newElement) {
CodeEditUtil.replaceChild(this, child, newElement);
}
@Override
protected void visitNode(TreeElement element) {
CodeEditUtil.setNodeGenerated(element, true);
super.visitNode(element);
}