diff --git a/CHANGELOG.adoc b/CHANGELOG.adoc index 355d54bdc..6807a50e3 100644 --- a/CHANGELOG.adoc +++ b/CHANGELOG.adoc @@ -11,6 +11,7 @@ This document provides a high-level view of the changes introduced by release. - Clear lock for JCEF preview to prevent a blank preview every time you open an AsciiDoc file (#1610) - Notify user when an Antora component descriptor misses the name (#1728) +- Allow disabling validation on individual code blocks (#830) === 0.43.2 diff --git a/doc/users-guide/modules/ROOT/images/hide-errors-in-source-blocks.png b/doc/users-guide/modules/ROOT/images/hide-errors-in-source-blocks.png new file mode 100644 index 000000000..f87138d36 Binary files /dev/null and b/doc/users-guide/modules/ROOT/images/hide-errors-in-source-blocks.png differ diff --git a/doc/users-guide/modules/ROOT/pages/faq/validation-for-asciidoc-files.adoc b/doc/users-guide/modules/ROOT/pages/faq/validation-for-asciidoc-files.adoc index c9593ff15..ef9926e4e 100644 --- a/doc/users-guide/modules/ROOT/pages/faq/validation-for-asciidoc-files.adoc +++ b/doc/users-guide/modules/ROOT/pages/faq/validation-for-asciidoc-files.adoc @@ -13,6 +13,40 @@ To do this, all files need to be in one project. If the IDE opens a single file and not a project with all related files, it might show validation errors where it shouldn't. +== Validation of source code snippets + +For source code with a specified language, the IDE will inject the language context and will show validation errors. + +[,java] +---- +System.out.println("Hello, world!"); +---- + +In the plugin's settings, a user can hide errors in source blocks for all languages, or for specific languages. + +image::hide-errors-in-source-blocks.png[] + +To prevent this on individual code blocks, add the option `novalidate` to the source block. +This option is a non-standard AsciiDoc option and specific to the AsciiDoc plugin for IntelliJ. + +.Adding the `novalidate` option to the beginning +[source,asciidoc] +----- +[%novalidate,java] +---- +System.out.println("Hello, world!"); +---- +----- + +.Adding the `novalidate` option to the `opts` attributes +[source,asciidoc] +----- +[,java,opts=novalidate] +---- +System.out.println("Hello, world!"); +---- +----- + == How to edit files as a project The user selects the menu item menu:File[Open...], then selects the folder and opens it. diff --git a/src/main/java/org/asciidoc/intellij/injection/CodeFenceHighlightInfoFilter.java b/src/main/java/org/asciidoc/intellij/injection/CodeFenceHighlightInfoFilter.java index 691bbe241..1bcc3a2cf 100644 --- a/src/main/java/org/asciidoc/intellij/injection/CodeFenceHighlightInfoFilter.java +++ b/src/main/java/org/asciidoc/intellij/injection/CodeFenceHighlightInfoFilter.java @@ -39,8 +39,11 @@ public boolean accept(@NotNull HighlightInfo highlightInfo, @Nullable PsiFile fi PsiLanguageInjectionHost injectionHost = manager.getInjectionHost(file); PsiFile topLevelFile = manager.getTopLevelFile(file); if (topLevelFile.getFileType() == AsciiDocFileType.INSTANCE - && injectionHost instanceof AsciiDocElementWithLanguage) { + && injectionHost instanceof AsciiDocElementWithLanguage host) { if (!SEVERITIES.contains(highlightInfo.getSeverity())) { + if (!host.validateContent()) { + return false; + } if (AsciiDocApplicationSettings.getInstance().getAsciiDocPreviewSettings().isHideErrorsInSourceBlocks()) { return false; } diff --git a/src/main/java/org/asciidoc/intellij/psi/AsciiDocElementWithLanguage.java b/src/main/java/org/asciidoc/intellij/psi/AsciiDocElementWithLanguage.java index 07e6921be..d73de98d7 100644 --- a/src/main/java/org/asciidoc/intellij/psi/AsciiDocElementWithLanguage.java +++ b/src/main/java/org/asciidoc/intellij/psi/AsciiDocElementWithLanguage.java @@ -7,4 +7,8 @@ public interface AsciiDocElementWithLanguage extends PsiLanguageInjectionHost { String getFenceLanguage(); TextRange getContentTextRange(); + + default boolean validateContent() { + return true; + } } diff --git a/src/main/java/org/asciidoc/intellij/psi/AsciiDocListing.java b/src/main/java/org/asciidoc/intellij/psi/AsciiDocListing.java index 8836502a1..d6c2b8a29 100644 --- a/src/main/java/org/asciidoc/intellij/psi/AsciiDocListing.java +++ b/src/main/java/org/asciidoc/intellij/psi/AsciiDocListing.java @@ -1,7 +1,6 @@ package org.asciidoc.intellij.psi; import com.intellij.openapi.util.TextRange; -import com.intellij.psi.LiteralTextEscaper; import com.intellij.psi.PsiElement; import com.intellij.psi.PsiElementVisitor; import com.intellij.psi.tree.IElementType; @@ -26,47 +25,32 @@ public void accept(@NotNull PsiElementVisitor visitor) { super.accept(visitor); } - @Override - public Type getType() { - return Type.LISTING; - } - - @Override - public String getDefaultTitle() { - return "Listing"; - } - @Override public TextRange getContentTextRange() { return getContentTextRange(AsciiDocTokenTypes.LISTING_BLOCK_DELIMITER, AsciiDocTokenTypes.LITERAL_BLOCK_DELIMITER); } - @NotNull @Override - public LiteralTextEscaper createLiteralTextEscaper() { - return new LiteralTextEscaper(this) { - @Override - public boolean decode(@NotNull TextRange rangeInsideHost, @NotNull StringBuilder outChars) { - outChars.append(rangeInsideHost.substring(myHost.getText())); - return true; - } - - @Override - public int getOffsetInHost(int offsetInDecoded, @NotNull TextRange rangeInsideHost) { - return rangeInsideHost.getStartOffset() + offsetInDecoded; - } - - @NotNull - @Override - public TextRange getRelevantTextRange() { - return myHost.getContentTextRange(); - } - - @Override - public boolean isOneLine() { - return false; + public boolean validateContent() { + final PsiElement element = findPsiChildByType(AsciiDocElementTypes.BLOCK_ATTRIBUTES); + if (element != null) { + AsciiDocBlockAttributes blockAttributes = PsiTreeUtil.findChildOfType(this, AsciiDocBlockAttributes.class); + if (blockAttributes != null) { + String[] attr = blockAttributes.getAttributes(); + if (attr.length > 0 && attr[0].contains("%novalidate")) { + return false; + } + String opts = blockAttributes.getAttribute("opts"); + if (opts != null) { + for (String opt : opts.split(",")) { + if (opt.trim().equals("novalidate")) { + return false; + } + } + } } - }; + } + return true; } @Override @@ -82,7 +66,7 @@ public String getFenceLanguage() { return null; } else if (attr.length >= 1) { firstAttr = attr[0]; - int locationOfPercent = firstAttr.indexOf("%"); // this handles for example "plantuml%interactive" + int locationOfPercent = firstAttr.indexOf("%"); // this handles, for example, "plantuml%interactive" if (locationOfPercent != -1) { firstAttr = firstAttr.substring(0, locationOfPercent); }