mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-09-27 10:03:11 +07:00
HTML: mimeType support in the script tag.
This commit is contained in:
@@ -20,6 +20,7 @@ import com.intellij.openapi.fileTypes.FileType;
|
||||
import com.intellij.openapi.fileTypes.FileTypeRegistry;
|
||||
import com.intellij.openapi.fileTypes.LanguageFileType;
|
||||
import com.intellij.openapi.util.UserDataHolderBase;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.util.ArrayUtil;
|
||||
import gnu.trove.THashMap;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
@@ -40,7 +41,10 @@ import java.util.*;
|
||||
public abstract class Language extends UserDataHolderBase {
|
||||
private static final Logger LOG = Logger.getInstance("#com.intellij.lang.Language");
|
||||
|
||||
private static final Map<Class<? extends Language>, Language> ourRegisteredLanguages = Collections.synchronizedMap(new THashMap<Class<? extends Language>, Language>());
|
||||
private static final Map<Class<? extends Language>, Language> ourRegisteredLanguages =
|
||||
Collections.synchronizedMap(new THashMap<Class<? extends Language>, Language>());
|
||||
private static final Map<String, List<Language>> ourRegisteredMimeTypes =
|
||||
Collections.synchronizedMap(new THashMap<String, List<Language>>());
|
||||
private static final Map<String, Language> ourRegisteredIDs = new THashMap<String, Language>();
|
||||
private final Language myBaseLanguage;
|
||||
private final String myID;
|
||||
@@ -69,12 +73,28 @@ public abstract class Language extends UserDataHolderBase {
|
||||
Class<? extends Language> langClass = getClass();
|
||||
Language prev = ourRegisteredLanguages.put(langClass, this);
|
||||
if (prev != null) {
|
||||
LOG.error("Language of '" + langClass + "' is already registered: "+prev);
|
||||
LOG.error("Language of '" + langClass + "' is already registered: " + prev);
|
||||
return;
|
||||
}
|
||||
prev = ourRegisteredIDs.put(ID, this);
|
||||
if (prev != null) {
|
||||
LOG.error("Language with ID '" + ID + "' is already registered: "+prev.getClass());
|
||||
LOG.error("Language with ID '" + ID + "' is already registered: " + prev.getClass());
|
||||
}
|
||||
for (String mimeType : mimeTypes) {
|
||||
if (StringUtil.isEmpty(mimeType)) {
|
||||
continue;
|
||||
}
|
||||
List<Language> languagesByMimeType = ourRegisteredMimeTypes.get(mimeType);
|
||||
if (languagesByMimeType == null) {
|
||||
synchronized (ourRegisteredMimeTypes) {
|
||||
languagesByMimeType = ourRegisteredMimeTypes.get(mimeType);
|
||||
if (languagesByMimeType == null) {
|
||||
languagesByMimeType = Collections.synchronizedList(new ArrayList<Language>());
|
||||
ourRegisteredMimeTypes.put(mimeType, languagesByMimeType);
|
||||
}
|
||||
}
|
||||
}
|
||||
languagesByMimeType.add(this);
|
||||
}
|
||||
if (baseLanguage != null) {
|
||||
baseLanguage.myDialects.add(this);
|
||||
@@ -98,6 +118,16 @@ public abstract class Language extends UserDataHolderBase {
|
||||
return (T)ourRegisteredLanguages.get(klass);
|
||||
}
|
||||
|
||||
/**
|
||||
* @param mimeType of the particular language.
|
||||
* @return collection of all languages for the given <code>mimeType</code>.
|
||||
*/
|
||||
@NotNull
|
||||
public static Collection<Language> findInstancesByMimeType(@Nullable String mimeType) {
|
||||
List<Language> result = mimeType != null ? ourRegisteredMimeTypes.get(mimeType) : null;
|
||||
return result != null ? Collections.unmodifiableCollection(result) : Collections.<Language>emptyList();
|
||||
}
|
||||
|
||||
|
||||
public String toString() {
|
||||
//noinspection HardCodedStringLiteral
|
||||
|
||||
@@ -34,7 +34,7 @@
|
||||
|
||||
<extensionPoint name="intentionAction"
|
||||
beanClass="com.intellij.codeInsight.intention.IntentionActionBean"/>
|
||||
|
||||
|
||||
<extensionPoint name="codeInsight.unresolvedReferenceQuickFixProvider"
|
||||
interface="com.intellij.codeInsight.quickfix.UnresolvedReferenceQuickFixProvider"/>
|
||||
|
||||
@@ -237,7 +237,7 @@
|
||||
<extensionPoint name="favoritesListProvider"
|
||||
interface="com.intellij.ide.favoritesTreeView.FavoritesListProvider"
|
||||
area="IDEA_PROJECT"/>
|
||||
|
||||
|
||||
<extensionPoint name="lang.emacs" beanClass="com.intellij.lang.LanguageExtensionPoint"/>
|
||||
|
||||
<!-- File-Based Index-->
|
||||
@@ -311,7 +311,7 @@
|
||||
|
||||
<extensionPoint name="psi.referenceContributor" beanClass="com.intellij.psi.impl.source.resolve.reference.PsiReferenceContributorEP"/>
|
||||
<extensionPoint name="psi.referenceProvider" beanClass="com.intellij.psi.PsiReferenceProviderBean"/>
|
||||
<extensionPoint name="patterns.patternClass" beanClass="com.intellij.patterns.compiler.PatternClassBean"/>
|
||||
<extensionPoint name="patterns.patternClass" beanClass="com.intellij.patterns.compiler.PatternClassBean"/>
|
||||
|
||||
<extensionPoint name="pom.declarationSearcher" interface="com.intellij.pom.PomDeclarationSearcher"/>
|
||||
|
||||
@@ -548,7 +548,7 @@
|
||||
|
||||
<extensionPoint name="project.converterProvider"
|
||||
interface="com.intellij.conversion.ConverterProvider"/>
|
||||
|
||||
|
||||
<extensionPoint name="treeCopyHandler"
|
||||
interface="com.intellij.psi.impl.source.tree.TreeCopyHandler"/>
|
||||
<extensionPoint name="treeGenerator"
|
||||
@@ -567,4 +567,9 @@
|
||||
beanClass="com.intellij.lang.LanguageExtensionPoint"/>
|
||||
|
||||
<extensionPoint name="moduleRendererFactory" interface="com.intellij.ide.util.ModuleRendererFactory"/>
|
||||
|
||||
<extensionPoint name="html.scriptContentProvider"
|
||||
beanClass="com.intellij.lang.LanguageExtensionPoint"/>
|
||||
<extensionPoint name="html.inlineScriptTokenTypesProvider"
|
||||
beanClass="com.intellij.lang.LanguageExtensionPoint"/>
|
||||
</extensionPoints>
|
||||
|
||||
@@ -0,0 +1,25 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.lang;
|
||||
|
||||
import com.intellij.openapi.fileTypes.FileType;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
|
||||
public interface HtmlInlineScriptTokenTypesProvider {
|
||||
IElementType getElementType();
|
||||
|
||||
FileType getFileType();
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.lang;
|
||||
|
||||
import com.intellij.lexer.Lexer;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
public interface HtmlScriptContentProvider {
|
||||
/**
|
||||
* @return instance of the <code>com.intellij.psi.tree.IElementType</code> to use in html script tag
|
||||
*/
|
||||
IElementType getScriptElementType();
|
||||
|
||||
/**
|
||||
* @return highlighting lexer to use in html script tag
|
||||
*/
|
||||
@Nullable
|
||||
Lexer getHighlightingLexer();
|
||||
}
|
||||
@@ -0,0 +1,31 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.lang;
|
||||
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
public class LanguageHtmlInlineScriptTokenTypesProvider extends LanguageExtension<HtmlInlineScriptTokenTypesProvider> {
|
||||
public final static LanguageHtmlInlineScriptTokenTypesProvider INSTANCE = new LanguageHtmlInlineScriptTokenTypesProvider();
|
||||
|
||||
public LanguageHtmlInlineScriptTokenTypesProvider() {
|
||||
super("com.intellij.html.inlineScriptTokenTypesProvider");
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public static HtmlInlineScriptTokenTypesProvider getInlineScriptProvider(@Nullable Language language) {
|
||||
return language == null ? null : INSTANCE.forLanguage(language);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
* Copyright 2000-2012 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.lang;
|
||||
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
|
||||
public class LanguageHtmlScriptContentProvider extends LanguageExtension<HtmlScriptContentProvider> {
|
||||
public final static LanguageHtmlScriptContentProvider INSTANCE = new LanguageHtmlScriptContentProvider();
|
||||
|
||||
public LanguageHtmlScriptContentProvider() {
|
||||
super("com.intellij.html.scriptContentProvider");
|
||||
}
|
||||
|
||||
public static HtmlScriptContentProvider getScriptContentProvider(@NotNull Language language) {
|
||||
return INSTANCE.forLanguage(language);
|
||||
}
|
||||
}
|
||||
@@ -16,13 +16,19 @@
|
||||
package com.intellij.lexer;
|
||||
|
||||
import com.intellij.codeInsight.completion.CompletionUtil;
|
||||
import com.intellij.lang.HtmlScriptContentProvider;
|
||||
import com.intellij.lang.Language;
|
||||
import com.intellij.lang.LanguageHtmlScriptContentProvider;
|
||||
import com.intellij.openapi.util.text.StringUtil;
|
||||
import com.intellij.psi.impl.source.tree.TreeUtil;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import com.intellij.psi.tree.TokenSet;
|
||||
import com.intellij.psi.xml.XmlTokenType;
|
||||
import com.intellij.util.text.CharArrayUtil;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.util.Collection;
|
||||
import java.util.HashMap;
|
||||
|
||||
/**
|
||||
@@ -36,11 +42,17 @@ abstract class BaseHtmlLexer extends DelegateLexer {
|
||||
private static final int SEEN_ATTRIBUTE = 0x200;
|
||||
private static final int SEEN_CONTENT_TYPE = 0x400;
|
||||
protected static final int BASE_STATE_SHIFT = 11;
|
||||
@Nullable
|
||||
protected static Language ourDefaultLanguage = Language.findLanguageByID("JavaScript");
|
||||
|
||||
private boolean seenTag;
|
||||
private boolean seenAttribute;
|
||||
private boolean seenStyle;
|
||||
private boolean seenScript;
|
||||
|
||||
@Nullable
|
||||
protected String scriptType = null;
|
||||
|
||||
private final boolean caseInsensitive;
|
||||
private boolean seenContentType;
|
||||
private CharSequence cachedBufferSequence;
|
||||
@@ -96,7 +108,7 @@ abstract class BaseHtmlLexer extends DelegateLexer {
|
||||
|
||||
final boolean style = name.equals(TOKEN_STYLE);
|
||||
final int state = getState() & BASE_STATE_MASK;
|
||||
final boolean script = name.equals(TOKEN_SCRIPT) ||
|
||||
final boolean script = name.equals(TOKEN_SCRIPT) ||
|
||||
((name.startsWith(TOKEN_ON) && name.indexOf(':') == -1 && !isHtmlTagState(state)));
|
||||
|
||||
if (style || script) {
|
||||
@@ -136,9 +148,12 @@ abstract class BaseHtmlLexer extends DelegateLexer {
|
||||
return; // something invalid
|
||||
}
|
||||
|
||||
@NonNls String name = TreeUtil.getTokenText(lexer);
|
||||
if (caseInsensitive) name = name.toLowerCase();
|
||||
if (name.indexOf("javascript") == -1 && name.indexOf("jscript") == -1) {
|
||||
@NonNls String mimeType = TreeUtil.getTokenText(lexer);
|
||||
if (caseInsensitive) mimeType = mimeType.toLowerCase();
|
||||
if (supportMimeType(mimeType)) {
|
||||
scriptType = mimeType;
|
||||
}
|
||||
else {
|
||||
seenScript = false;
|
||||
seenTag = true; // will be switched of on tag name in end
|
||||
}
|
||||
@@ -146,6 +161,31 @@ abstract class BaseHtmlLexer extends DelegateLexer {
|
||||
}
|
||||
}
|
||||
|
||||
private boolean supportMimeType(String mimeType) {
|
||||
return findScriptContentProvider(mimeType) != null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
protected IElementType getCurrentScriptElementType() {
|
||||
HtmlScriptContentProvider scriptContentProvider = findScriptContentProvider(scriptType);
|
||||
return scriptContentProvider == null ? null : scriptContentProvider.getScriptElementType();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
protected static HtmlScriptContentProvider findScriptContentProvider(@Nullable String mimeType) {
|
||||
if (StringUtil.isEmpty(mimeType)) {
|
||||
return ourDefaultLanguage != null ? LanguageHtmlScriptContentProvider.getScriptContentProvider(ourDefaultLanguage) : null;
|
||||
}
|
||||
Collection<Language> instancesByMimeType = Language.findInstancesByMimeType(mimeType);
|
||||
for (Language language : instancesByMimeType) {
|
||||
HtmlScriptContentProvider scriptContentProvider = LanguageHtmlScriptContentProvider.getScriptContentProvider(language);
|
||||
if (scriptContentProvider != null) {
|
||||
return scriptContentProvider;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
class XmlTagClosedHandler implements TokenHandler {
|
||||
public void handleElement(Lexer lexer) {
|
||||
if (seenAttribute) {
|
||||
@@ -167,6 +207,7 @@ abstract class BaseHtmlLexer extends DelegateLexer {
|
||||
seenScript=false;
|
||||
seenAttribute=false;
|
||||
seenContentType=false;
|
||||
scriptType = null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -15,9 +15,14 @@
|
||||
*/
|
||||
package com.intellij.lexer;
|
||||
|
||||
import com.intellij.lang.HtmlInlineScriptTokenTypesProvider;
|
||||
import com.intellij.lang.HtmlScriptContentProvider;
|
||||
import com.intellij.lang.Language;
|
||||
import com.intellij.lang.LanguageHtmlInlineScriptTokenTypesProvider;
|
||||
import com.intellij.openapi.diagnostic.Logger;
|
||||
import com.intellij.openapi.fileTypes.FileType;
|
||||
import com.intellij.openapi.fileTypes.FileTypeManager;
|
||||
import com.intellij.openapi.fileTypes.SyntaxHighlighter;
|
||||
import com.intellij.openapi.fileTypes.SyntaxHighlighterFactory;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
import com.intellij.psi.xml.XmlTokenType;
|
||||
@@ -35,7 +40,14 @@ public class HtmlHighlightingLexer extends BaseHtmlLexer {
|
||||
protected Lexer elLexer;
|
||||
private boolean hasNoEmbeddments;
|
||||
private final static FileType ourStyleFileType = FileTypeManager.getInstance().getStdFileType("CSS");
|
||||
private static FileType ourScriptFileType;
|
||||
private static FileType ourInlineScriptFileType = null;
|
||||
|
||||
static {
|
||||
// At the moment only JS.
|
||||
HtmlInlineScriptTokenTypesProvider provider =
|
||||
LanguageHtmlInlineScriptTokenTypesProvider.getInlineScriptProvider(Language.findLanguageByID("JavaScript"));
|
||||
ourInlineScriptFileType = provider != null ? provider.getFileType() : null;
|
||||
}
|
||||
|
||||
public class XmlEmbeddmentHandler implements TokenHandler {
|
||||
public void handleElement(Lexer lexer) {
|
||||
@@ -109,11 +121,22 @@ public class HtmlHighlightingLexer extends BaseHtmlLexer {
|
||||
|
||||
newLexer = styleLexer;
|
||||
} else if (hasSeenScript()) {
|
||||
if (scriptLexer==null) {
|
||||
scriptLexer = (ourScriptFileType!=null)? SyntaxHighlighterFactory.getSyntaxHighlighter(ourScriptFileType, null, null).getHighlightingLexer():null;
|
||||
if (scriptLexer == null) {
|
||||
if (hasSeenTag()) {
|
||||
HtmlScriptContentProvider provider = findScriptContentProvider(scriptType);
|
||||
scriptLexer = provider != null ? provider.getHighlightingLexer() : null;
|
||||
}
|
||||
else if (hasSeenAttribute()) {
|
||||
SyntaxHighlighter syntaxHighlighter =
|
||||
(ourInlineScriptFileType != null) ? SyntaxHighlighterFactory.getSyntaxHighlighter(ourInlineScriptFileType, null, null) : null;
|
||||
scriptLexer = syntaxHighlighter != null ? syntaxHighlighter.getHighlightingLexer() : null;
|
||||
}
|
||||
}
|
||||
newLexer = scriptLexer;
|
||||
} else newLexer = createELLexer(newLexer);
|
||||
}
|
||||
else {
|
||||
newLexer = createELLexer(newLexer);
|
||||
}
|
||||
|
||||
if (newLexer!=null) {
|
||||
embeddedLexer = newLexer;
|
||||
@@ -189,10 +212,6 @@ public class HtmlHighlightingLexer extends BaseHtmlLexer {
|
||||
}
|
||||
}
|
||||
|
||||
public static void registerScriptFileType(FileType _scriptFileType) {
|
||||
ourScriptFileType = _scriptFileType;
|
||||
}
|
||||
|
||||
public int getState() {
|
||||
int state = super.getState();
|
||||
|
||||
@@ -203,7 +222,7 @@ public class HtmlHighlightingLexer extends BaseHtmlLexer {
|
||||
}
|
||||
|
||||
protected boolean isHtmlTagState(int state) {
|
||||
return state == _HtmlLexer.START_TAG_NAME || state == _HtmlLexer.END_TAG_NAME ||
|
||||
return state == _HtmlLexer.START_TAG_NAME || state == _HtmlLexer.END_TAG_NAME ||
|
||||
state == _HtmlLexer.START_TAG_NAME2 || state == _HtmlLexer.END_TAG_NAME2;
|
||||
}
|
||||
|
||||
|
||||
@@ -15,6 +15,9 @@
|
||||
*/
|
||||
package com.intellij.lexer;
|
||||
|
||||
import com.intellij.lang.HtmlInlineScriptTokenTypesProvider;
|
||||
import com.intellij.lang.Language;
|
||||
import com.intellij.lang.LanguageHtmlInlineScriptTokenTypesProvider;
|
||||
import com.intellij.openapi.extensions.Extensions;
|
||||
import com.intellij.psi.TokenType;
|
||||
import com.intellij.psi.tree.IElementType;
|
||||
@@ -26,7 +29,6 @@ import com.intellij.psi.xml.XmlTokenType;
|
||||
public class HtmlLexer extends BaseHtmlLexer {
|
||||
private static IElementType ourStyleElementType;
|
||||
private static IElementType ourInlineStyleElementType;
|
||||
private static IElementType ourScriptElementType;
|
||||
private static IElementType ourInlineScriptElementType;
|
||||
|
||||
static {
|
||||
@@ -37,6 +39,10 @@ public class HtmlLexer extends BaseHtmlLexer {
|
||||
ourInlineStyleElementType = extension.getInlineElementType();
|
||||
}
|
||||
}
|
||||
// At the moment only JS.
|
||||
HtmlInlineScriptTokenTypesProvider provider =
|
||||
LanguageHtmlInlineScriptTokenTypesProvider.getInlineScriptProvider(ourDefaultLanguage);
|
||||
ourInlineScriptElementType = provider != null ? provider.getElementType() : null;
|
||||
}
|
||||
|
||||
private IElementType myTokenType;
|
||||
@@ -69,9 +75,10 @@ public class HtmlLexer extends BaseHtmlLexer {
|
||||
tokenType = ourInlineStyleElementType;
|
||||
}
|
||||
} else if (hasSeenScript()) {
|
||||
if (hasSeenTag() && ourScriptElementType!=null && isStartOfEmbeddmentTagContent(tokenType)) {
|
||||
IElementType currentScriptElementType = getCurrentScriptElementType();
|
||||
if (hasSeenTag() && currentScriptElementType != null && isStartOfEmbeddmentTagContent(tokenType)) {
|
||||
myTokenEnd = skipToTheEndOfTheEmbeddment();
|
||||
tokenType = ourScriptElementType;
|
||||
tokenType = currentScriptElementType;
|
||||
} else if (hasSeenAttribute() && isStartOfEmbeddmentAttributeValue(tokenType) && ourInlineScriptElementType!=null) {
|
||||
myTokenEnd = skipToTheEndOfTheEmbeddment();
|
||||
tokenType = ourInlineScriptElementType;
|
||||
@@ -118,9 +125,4 @@ public class HtmlLexer extends BaseHtmlLexer {
|
||||
}
|
||||
return super.getTokenEnd();
|
||||
}
|
||||
|
||||
public static void setScriptElementTypes(final IElementType scriptElementType, final IElementType inlineScriptElementType) {
|
||||
ourScriptElementType = scriptElementType;
|
||||
ourInlineScriptElementType = inlineScriptElementType;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1,15 +1,15 @@
|
||||
package com.intellij.codeInsight;
|
||||
|
||||
import com.intellij.lang.ASTFactory;
|
||||
import com.intellij.lang.ASTNode;
|
||||
import com.intellij.lang.LanguageASTFactory;
|
||||
import com.intellij.lang.LanguageParserDefinitions;
|
||||
import com.intellij.lang.*;
|
||||
import com.intellij.lang.dtd.DTDLanguage;
|
||||
import com.intellij.lang.dtd.DTDParserDefinition;
|
||||
import com.intellij.lang.html.HTMLLanguage;
|
||||
import com.intellij.lang.html.HTMLParserDefinition;
|
||||
import com.intellij.lang.xml.XMLLanguage;
|
||||
import com.intellij.lang.xml.XMLParserDefinition;
|
||||
import com.intellij.lang.xml.XmlASTFactory;
|
||||
import com.intellij.lexer.FilterLexer;
|
||||
import com.intellij.lexer.HtmlEmbeddedTokenTypesProvider;
|
||||
import com.intellij.lexer.Lexer;
|
||||
import com.intellij.lexer.XmlLexer;
|
||||
import com.intellij.openapi.application.Result;
|
||||
@@ -29,6 +29,7 @@ import com.intellij.testFramework.ParsingTestCase;
|
||||
import com.intellij.testFramework.PlatformTestUtil;
|
||||
import com.intellij.util.ThrowableRunnable;
|
||||
import org.jetbrains.annotations.NonNls;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import java.io.File;
|
||||
|
||||
@@ -167,24 +168,28 @@ public class XmlParsingTest extends ParsingTestCase {
|
||||
doTestXml(loadFile("manyErrors.xml"));
|
||||
}
|
||||
|
||||
public void _testLexerPerformance1() throws Exception{
|
||||
public void _testLexerPerformance1() throws Exception {
|
||||
final String text = loadFile("pallada.xml");
|
||||
XmlLexer lexer = new XmlLexer();
|
||||
doLex(lexer, text);
|
||||
final FilterLexer filterLexer = new FilterLexer(new XmlLexer(),
|
||||
new FilterLexer.SetFilter(LanguageParserDefinitions.INSTANCE.forLanguage(XMLLanguage.INSTANCE).getWhitespaceTokens()));
|
||||
new FilterLexer.SetFilter(
|
||||
LanguageParserDefinitions.INSTANCE.forLanguage(XMLLanguage.INSTANCE)
|
||||
.getWhitespaceTokens()));
|
||||
doLex(filterLexer, text);
|
||||
doLex(lexer, text);
|
||||
doLex(filterLexer, text);
|
||||
doLex(filterLexer, text);
|
||||
}
|
||||
|
||||
public void _testLexerPerformance2() throws Exception{
|
||||
|
||||
public void _testLexerPerformance2() throws Exception {
|
||||
final String text = loadFile("performance2.xml");
|
||||
XmlLexer lexer = new XmlLexer();
|
||||
doLex(lexer, text);
|
||||
final FilterLexer filterLexer = new FilterLexer(new XmlLexer(),
|
||||
new FilterLexer.SetFilter(LanguageParserDefinitions.INSTANCE.forLanguage(XMLLanguage.INSTANCE).getWhitespaceTokens()));
|
||||
new FilterLexer.SetFilter(
|
||||
LanguageParserDefinitions.INSTANCE.forLanguage(XMLLanguage.INSTANCE)
|
||||
.getWhitespaceTokens()));
|
||||
doLex(filterLexer, text);
|
||||
doLex(lexer, text);
|
||||
for (int i = 0; i < 20; i++) {
|
||||
@@ -196,7 +201,7 @@ public class XmlParsingTest extends ParsingTestCase {
|
||||
lexer.start(text);
|
||||
long time = System.currentTimeMillis();
|
||||
int count = 0;
|
||||
while(lexer.getTokenType() != null){
|
||||
while (lexer.getTokenType() != null) {
|
||||
lexer.advance();
|
||||
count++;
|
||||
}
|
||||
@@ -210,22 +215,22 @@ public class XmlParsingTest extends ParsingTestCase {
|
||||
}
|
||||
|
||||
|
||||
public void _testPerformance1() throws Exception{
|
||||
public void _testPerformance1() throws Exception {
|
||||
final String text = loadFile("pallada.xml");
|
||||
long time = System.currentTimeMillis();
|
||||
final PsiFile file = createFile("test.xml", text);
|
||||
transformAllChildren(file.getNode());
|
||||
System.out.println("Old parsing took " + (System.currentTimeMillis() - time) + "ms");
|
||||
int index = 0;
|
||||
while(index++ < 10){
|
||||
while (index++ < 10) {
|
||||
newParsing(text);
|
||||
}
|
||||
LeafElement firstLeaf = TreeUtil.findFirstLeaf(file.getNode());
|
||||
index = 0;
|
||||
do{
|
||||
do {
|
||||
index++;
|
||||
}
|
||||
while((firstLeaf = TreeUtil.nextLeaf(firstLeaf, null)) != null);
|
||||
while ((firstLeaf = TreeUtil.nextLeaf(firstLeaf, null)) != null);
|
||||
System.out.println("For " + index + " lexems");
|
||||
}
|
||||
|
||||
@@ -237,7 +242,7 @@ public class XmlParsingTest extends ParsingTestCase {
|
||||
|
||||
System.gc();
|
||||
System.gc();
|
||||
|
||||
|
||||
new WriteCommandAction(getProject(), file) {
|
||||
@Override
|
||||
protected void run(final Result result) throws Throwable {
|
||||
@@ -256,22 +261,22 @@ public class XmlParsingTest extends ParsingTestCase {
|
||||
}.execute();
|
||||
}
|
||||
|
||||
public void _testPerformance2() throws Exception{
|
||||
public void _testPerformance2() throws Exception {
|
||||
final String text = loadFile("performance2.xml");
|
||||
long time = System.currentTimeMillis();
|
||||
final PsiFile file = createFile("test.xml", text);
|
||||
transformAllChildren(file.getNode());
|
||||
System.out.println("Old parsing took " + (System.currentTimeMillis() - time) + "ms");
|
||||
int index = 0;
|
||||
while(index++ < 10){
|
||||
while (index++ < 10) {
|
||||
newParsing(text);
|
||||
}
|
||||
LeafElement firstLeaf = TreeUtil.findFirstLeaf(file.getNode());
|
||||
index = 0;
|
||||
do{
|
||||
do {
|
||||
index++;
|
||||
}
|
||||
while((firstLeaf = TreeUtil.nextLeaf(firstLeaf, null)) != null);
|
||||
while ((firstLeaf = TreeUtil.nextLeaf(firstLeaf, null)) != null);
|
||||
System.out.println("For " + index + " lexems");
|
||||
}
|
||||
|
||||
@@ -644,5 +649,31 @@ public class XmlParsingTest extends ParsingTestCase {
|
||||
doTestXml("<!DOCTYPE x3 [<!NOTATION data-sources SYSTEM \"x3\">]>");
|
||||
}
|
||||
|
||||
public void testCustomMimeType() throws Exception {
|
||||
final Language language = new MyLanguage();
|
||||
addExplicitExtension(LanguageHtmlScriptContentProvider.INSTANCE, language, new HtmlScriptContentProvider() {
|
||||
@Override
|
||||
public IElementType getScriptElementType() {
|
||||
return new IElementType("MyElementType", language);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Lexer getHighlightingLexer() {
|
||||
return null;
|
||||
}
|
||||
});
|
||||
addExplicitExtension(LanguageParserDefinitions.INSTANCE, HTMLLanguage.INSTANCE, new HTMLParserDefinition());
|
||||
addExplicitExtension(LanguageASTFactory.INSTANCE, HTMLLanguage.INSTANCE, new XmlASTFactory());
|
||||
registerExtensionPoint(new ExtensionPointName<HtmlEmbeddedTokenTypesProvider>("com.intellij.html.embeddedTokenTypesProvider"),
|
||||
HtmlEmbeddedTokenTypesProvider.class);
|
||||
myLanguage = HTMLLanguage.INSTANCE;
|
||||
doTest("<script type=\"application/custom\">Custom Script</script>", "test.html");
|
||||
}
|
||||
|
||||
static class MyLanguage extends Language {
|
||||
protected MyLanguage() {
|
||||
super("MyLanguage", "application/custom");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,21 @@
|
||||
HtmlFile:test.html
|
||||
PsiElement(HTML_DOCUMENT)
|
||||
PsiElement(XML_PROLOG)
|
||||
<empty list>
|
||||
HtmlTag:script
|
||||
XmlToken:XML_START_TAG_START('<')
|
||||
XmlToken:XML_NAME('script')
|
||||
PsiWhiteSpace(' ')
|
||||
PsiElement(XML_ATTRIBUTE)
|
||||
XmlToken:XML_NAME('type')
|
||||
XmlToken:XML_EQ('=')
|
||||
PsiElement(XML_ATTRIBUTE_VALUE)
|
||||
XmlToken:XML_ATTRIBUTE_VALUE_START_DELIMITER('"')
|
||||
XmlToken:XML_ATTRIBUTE_VALUE_TOKEN('application/custom')
|
||||
XmlToken:XML_ATTRIBUTE_VALUE_END_DELIMITER('"')
|
||||
XmlToken:XML_TAG_END('>')
|
||||
XmlText
|
||||
PsiElement(MyElementType)('Custom Script')
|
||||
XmlToken:XML_END_TAG_START('</')
|
||||
XmlToken:XML_NAME('script')
|
||||
XmlToken:XML_TAG_END('>')
|
||||
Reference in New Issue
Block a user