How to insert php-statement into html tag ?

I have some html code in my PHP file. For example, 

<div id="someId"><div>

I need to insert some PHP group statement into DIV tag:

<div id="someId"><?=SomeClass::getSomeString(); ?><div>

But I can't create PsiElement with text "<?=SomeClass::getSomeString(); ?>" :(

The only way I found:

PhpPsiElementFactory.createPhpPsiFromText(element.getProject(), PhpElementTypes.ANY_GROUP_STATEMENT,"=SomeClass::getSomeString();")

but result looks like this:

<div id="someId"><?php

=SomeClass::getSomeString(); ?><div>

Is there some way to solve this problem?

0
正式评论

> But I can't create PsiElement with text "<?=SomeClass::getSomeString(); ?>" :(

This is because the string consists of actually 4 PsiElements: an opening tag, an echo statement, a white space, and a closing tag. Let's modify your code a little bit.

PhpPsiElementFactory.createPhpPsiFromText(element.getProject(), PhpElementTypes.ANY_GROUP_STATEMENT,"?><?=SomeClass::getSomeString(); ?>")

Now you only need to find the second opening tag and the second closing tag. After that, you can use PsiElement#addRange* methods to insert a range of elements.

Alternatively, you can use the IntelliJ platform API directly.

PsiFileFactory.getInstance(element.getProject()).createFileFromText("temp.php", PhpFileType.INSTANCE, "<?=SomeClass::getSomeString(); ?>");

The previous line will create a new PHP file. It will consist only of your code so it'll be easier to manipulate with it.

I hope I've answered your question. If something is still unclear, feel free to provide us with more details to better understand your needs.

Thanks :)

Yep, the first variant does work...but I've got another problem :)

PsiElement groupStatementPsiElement = PhpPsiElementFactory.createPhpPsiFromText(element.getProject(), PhpElementTypes.ANY_GROUP_STATEMENT,"?><?=SomeClass::getSomeString();?>");
PsiElement secondOpenTag = groupStatementPsiElement.findElementAt(8);//can't find the right way to find open tag.
PsiElement closeTag = groupStatementPsiElement.getLastChild();//get last close tag
if(secondOpenTag != null && ((LeafPsiElement) secondOpenTag).getElementType() == PhpTokenTypes.PHP_ECHO_OPENING_TAG)
{
//divPsiElement is HtmlTagImlp instance
divPsiElement.addRange(secondOpenTag, closeTag);
}

 

the code above produces an exception:

 

Assertion failed
java.lang.Throwable
at com.intellij.openapi.diagnostic.Logger.assertTrue(Logger.java:168)
at com.intellij.openapi.diagnostic.Logger.assertTrue(Logger.java:177)
at com.intellij.psi.impl.source.xml.XmlTagImpl.addInternal(XmlTagImpl.java:1084)
at com.intellij.psi.impl.source.xml.XmlTagImpl.addInternal(XmlTagImpl.java:1042)
at com.intellij.psi.impl.source.tree.SharedImplUtil.addRange(SharedImplUtil.java:146)
at com.intellij.psi.impl.source.tree.CompositePsiElement.addRange(CompositePsiElement.java:174)
at com.bitrixsoft.php.lang.quickfix.OneLangPhraseCreate.createLangAction(OneLangPhraseCreate.java:95)
at com.intellij.openapi.command.impl.CoreCommandProcessor.runUndoTransparentAction(CoreCommandProcessor.java:323)
at com.bitrixsoft.php.lang.quickfix.OneLangPhraseCreate.lambda$null$0(OneLangPhraseCreate.java:55)
at com.intellij.openapi.application.impl.ApplicationImpl.runWriteAction(ApplicationImpl.java:1023)
at com.bitrixsoft.php.lang.quickfix.OneLangPhraseCreate.lambda$new$1(OneLangPhraseCreate.java:54)
at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2022)
at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2348)
at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:402)
at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:259)
at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:252)
at java.awt.Component.processMouseEvent(Component.java:6535)
at javax.swing.JComponent.processMouseEvent(JComponent.java:3324)
at java.awt.Component.processEvent(Component.java:6300)
at java.awt.Container.processEvent(Container.java:2236)
at java.awt.Component.dispatchEventImpl(Component.java:4891)
at java.awt.Container.dispatchEventImpl(Container.java:2294)
at java.awt.Component.dispatchEvent(Component.java:4713)
at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4888)
at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4525)
at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4466)
at java.awt.Container.dispatchEventImpl(Container.java:2280)
at java.awt.Window.dispatchEventImpl(Window.java:2750)
at java.awt.Component.dispatchEvent(Component.java:4713)
at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:758)
at java.awt.EventQueue.access$500(EventQueue.java:97)
at java.awt.EventQueue$3.run(EventQueue.java:709)
at java.awt.EventQueue$3.run(EventQueue.java:703)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:86)
at java.awt.EventQueue$4.run(EventQueue.java:731)
at java.awt.EventQueue$4.run(EventQueue.java:729)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.awt.EventQueue.dispatchEvent(EventQueue.java:728)
at com.intellij.ide.IdeEventQueue.h(IdeEventQueue.java:827)
at com.intellij.ide.IdeEventQueue._dispatchEvent(IdeEventQueue.java:651)
at com.intellij.ide.IdeEventQueue.dispatchEvent(IdeEventQueue.java:365)
at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:201)
at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:109)
at java.awt.WaitDispatchSupport$2.run(WaitDispatchSupport.java:184)
at java.awt.WaitDispatchSupport$4.run(WaitDispatchSupport.java:229)
at java.awt.WaitDispatchSupport$4.run(WaitDispatchSupport.java:227)
at java.security.AccessController.doPrivileged(Native Method)
at java.awt.WaitDispatchSupport.enter(WaitDispatchSupport.java:227)
at java.awt.Dialog.show(Dialog.java:1084)
at java.awt.Component.show(Component.java:1673)
at java.awt.Component.setVisible(Component.java:1625)
at java.awt.Window.setVisible(Window.java:1014)
at java.awt.Dialog.setVisible(Dialog.java:1005)
at com.bitrixsoft.php.lang.quickfix.OneLangPhraseCreate.main(OneLangPhraseCreate.java:168)
at com.bitrixsoft.php.lang.quickfix.CreateLangPhraseIntentionAction.show(CreateLangPhraseIntentionAction.java:81)
at com.bitrixsoft.php.lang.quickfix.CreateLangPhraseIntentionAction.invoke(CreateLangPhraseIntentionAction.java:73)
at com.intellij.codeInsight.intention.impl.ShowIntentionActionsHandler.b(ShowIntentionActionsHandler.java:196)
at com.intellij.codeInsight.intention.impl.ShowIntentionActionsHandler.a(ShowIntentionActionsHandler.java:200)
at com.intellij.codeInsight.intention.impl.ShowIntentionActionsHandler.b(ShowIntentionActionsHandler.java:186)
at com.intellij.openapi.application.TransactionGuardImpl.a(TransactionGuardImpl.java:86)
at com.intellij.openapi.application.TransactionGuardImpl.submitTransactionAndWait(TransactionGuardImpl.java:151)
at com.intellij.codeInsight.intention.impl.ShowIntentionActionsHandler.a(ShowIntentionActionsHandler.java:185)
at com.intellij.openapi.command.impl.CoreCommandProcessor.a(CoreCommandProcessor.java:149)
at com.intellij.openapi.command.impl.CoreCommandProcessor.executeCommand(CoreCommandProcessor.java:109)
at com.intellij.openapi.command.impl.CoreCommandProcessor.executeCommand(CoreCommandProcessor.java:99)
at com.intellij.openapi.command.impl.CoreCommandProcessor.executeCommand(CoreCommandProcessor.java:85)
at com.intellij.codeInsight.intention.impl.ShowIntentionActionsHandler.chooseActionAndInvoke(ShowIntentionActionsHandler.java:184)
at com.intellij.codeInsight.intention.impl.IntentionListStep.b(IntentionListStep.java:273)
at com.intellij.openapi.application.TransactionGuardImpl.performUserActivity(TransactionGuardImpl.java:193)
at com.intellij.ui.popup.AbstractPopup.a(AbstractPopup.java:1396)
at java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:311)
at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:756)
at java.awt.EventQueue.access$500(EventQueue.java:97)
at java.awt.EventQueue$3.run(EventQueue.java:709)
at java.awt.EventQueue$3.run(EventQueue.java:703)
at java.security.AccessController.doPrivileged(Native Method)
at java.security.ProtectionDomain$JavaSecurityAccessImpl.doIntersectionPrivilege(ProtectionDomain.java:76)
at java.awt.EventQueue.dispatchEvent(EventQueue.java:726)
at com.intellij.ide.IdeEventQueue.h(IdeEventQueue.java:827)
at com.intellij.ide.IdeEventQueue._dispatchEvent(IdeEventQueue.java:655)
at com.intellij.ide.IdeEventQueue.dispatchEvent(IdeEventQueue.java:365)
at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:201)
at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:116)
at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:105)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:101)
at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:93)
at java.awt.EventDispatchThread.run(EventDispatchThread.java:82)

0

The second way works perfectly! 

PsiFile tempFile = PsiFileFactory.getInstance(element.getProject()).createFileFromText("temp.php", PhpFileType.INSTANCE, "<?="+stringExp+"?>");
PsiElement elementForReplacing = tempFile.getFirstChild();
element.replace(elementForReplacing);// element is innerHTML-content of my div

0

Well, I had to mention it from the very beginning. In general, it's not a good idea to insert PHP PSI elements into an HTML tree. Instead, you should just put your text directly into a document. It could look something like this (don't forget to commit a document afterward).

editor.getCaretModel().moveToOffset(offset);
EditorModificationUtil.insertStringAtCaret(editor, "<?=SomeClass::getSomeString(); ?>");
PsiDocumentManager.getInstance(getProject()).commitDocument(editor.getDocument());
0

请先登录再写评论。