2.0.5 • Published 12 months ago

@heppokofrontend/html-code-block-element v2.0.5

Weekly downloads
-
License
MIT
Repository
github
Last release
12 months ago

<code-block>

MIT License Published on NPM Published on webcomponents.org npm.io Maintainability Test Coverage Known Vulnerabilities @heppokofrontend/html-code-block-element

Code block custom element with syntax highlighting and copy button.

It has highlight.js for syntax highlighting.

Usage

DEMO: https://heppokofrontend.github.io/html-code-block-element/

<code-block language="html" label="example.html" controls>
  &lt;script&gt;console.log(true);&lt;/script&gt;
</code-block>

In browser

It can be used by loading html-code-block-element.common.min.js and one CSS theme.

The highlight.js style is available on CDN. You can also download the JS and CSS from the respective repositories and load them into your page.

<link
  rel="stylesheet"
  href="https://cdnjs.cloudflare.com/ajax/libs/highlight.js/11.1.0/styles/vs.min.css"
/>
<script
  src="https://cdn.jsdelivr.net/npm/@heppokofrontend/html-code-block-element/lib/html-code-block-element.common.min.js"
  defer
></script>

There are three versions of this library available.

  • html-code-block-element.common.min.js - One that supports only the popular languages.
  • html-code-block-element.all.min.js - One that enables all languages supported by highligh.js.
  • html-code-block-element.core.min.js - For developers who want to do their own hljs.registerLanguage().

Example

Note: The textarea element cannot be included in the content of the textarea element. If you want to include it, please use HTML Entity for the tag.

<code-block language="html" label="example.html" controls>
  <textarea><script>console.log(true);</script></textarea>
</code-block>

or

<code-block language="html" label="example.html" controls>
  &lt;script&gt;console.log(true);&lt;/script&gt;
</code-block>

Assumption specifications

  • Categories:
  • Contexts in which this element can be used:
    • Where flow content is expected.
  • Content model:
  • Tag omission in text/html:
    • Neither tag is omissible.
  • Content attributes:
    • Global attributes
    • controls - Show controls
    • notrim - Does't remove whitespace from both ends of a source
    • label - Give the code block a unique name. If omitted, it will always have the accessible name "Code Block".
    • language - Language name of the code. If omitted, it will be detected automatically.
  • Accessibility considerations:

DOM interface

[Exposed=Window]
interface HTMLCodeBlockElement : HTMLElement {
  [HTMLConstructor] constructor();

  [CEReactions] attribute boolean controls;
  [CEReactions] attribute boolean notrim;
  [CEReactions] attribute DOMString label;
  [CEReactions] attribute DOMString language;
  [CEReactions] attribute DOMString value;
};

In development

Installation:

npm install --save @heppokofrontend/html-code-block-element

Usage:

The customElements.define() will also be included.

// For highlighting, `highlight.js/lib/common` will be used.
import '@heppokofrontend/html-code-block-element';
// For highlighting, `highlight.js` will be used.
import '@heppokofrontend/html-code-block-element/dist/index.all';
// For highlighting, `highlight.js/lib/code` will be used.
import '@heppokofrontend/html-code-block-element/dist/index.core';

If you are using purely constructors:

import HTMLCodeBlockElement from '@heppokofrontend/html-code-block-element/dist/class/HTMLCodeBlockElement';

Use in React

This package contains the global type files for React.

  • React.CodeBlockHTMLAttributes
  • code-block in JSX.IntrinsicElements

* CSS needs to be loaded separately.

// CodeBlock.tsx
import {CodeBlockProps} from '@heppokofrontend/html-code-block-element/dist/manual';
import styleSheet from '@heppokofrontend/html-code-block-element/dist/styleSheet';
import hljs from 'highlight.js/lib/common';
import Head from 'next/head';
import {useEffect} from 'react';

declare module 'react' {
  // A type for the properties of a function component
  interface CodeBlockHTMLAttributes<T> extends HTMLAttributes<T> {
    /** The accessible name of code block */
    label?: string | undefined;
    /** The Language name */
    language?: string | undefined;
    /** The flag to display the UI */
    controls?: boolean;
  }
}

declare global {
  // A type for JSX markup
  namespace JSX {
    interface IntrinsicElements {
      'code-block': CodeBlockProps;
    }
  }
}

type Props = Omit<React.CodeBlockHTMLAttributes<HTMLElement>, 'className'>;

let isLoaded = false;

export const CodeBlock = ({children, ...props}: Props) => {
  useEffect(() => {
    const loadWebComponent = async () => {
      const {HTMLCodeBlockElement, createHighlightCallback} = await import(
        '@heppokofrontend/html-code-block-element/dist/manual'
      );

      HTMLCodeBlockElement.highlight = createHighlightCallback(hljs);
      customElements.define('code-block', HTMLCodeBlockElement);
    };

    if (!isLoaded) {
      isLoaded = true;
      loadWebComponent();
    }
  }, []);

  return (
    <>
      <Head>
        <style>{styleSheet}</style>
      </Head>
      <code-block {...props}>{children}</code-block>
    </>
  );
};

Use as constructor

Manual setup:

// 1. Import
import hljs from 'highlight.js/lib/core';
import javascript from 'highlight.js/lib/languages/javascript';
import HTMLCodeBlockElement from '@heppokofrontend/html-code-block-element/dist/class/HTMLCodeBlockElement';
//  or import { HTMLCodeBlockElement } from '@heppokofrontend/html-code-block-element';

// Support JavaScript
hljs.registerLanguage('javascript', javascript);

// 2. Set endgine
/**
 * Example: Callback to be called internally
 * @param {string} src - Source code string for highlight
 * @param {{ language: string }} options - Option for highlight
 * @returns {{ markup: string }} - Object of the highlight result
 */
HTMLCodeBlockElement.highlight = function (src, options) {
  if (
    // Verifying the existence of a language
    options?.language &&
    hljs.getLanguage(options.language)
  ) {
    const {value} = hljs.highlight(src, options);

    return {
      markup: value,
    };
  }

  return {
    markup: hljs.highlightAuto(src).value,
  };
};

// 3. Define
customElements.define('code-block', HTMLCodeBlockElement);

// 4. Make
const cbElm = new HTMLCodeBlockElement();

// 5. Assign
cbElm.language = 'javascript';
cbElm.label = 'your label';
cbElm.value = `const hoge = true;

console.log(hoge);`;

// 6. Append
document.body.append(cbElm); // Render at the same time
Syntax

No params.

new HTMLCodeBlockElement();

Support browser

  • Chrome
  • Safari
  • Firefox
  • Edge
2.0.5

12 months ago

2.0.4

12 months ago

2.0.3

1 year ago

2.0.2

1 year ago

2.0.1

1 year ago

2.0.0

1 year ago

1.1.1

3 years ago

1.1.0

3 years ago

1.0.7

3 years ago

1.0.6

3 years ago

1.0.5

3 years ago

1.0.4

3 years ago

1.0.2

3 years ago

1.0.1

3 years ago

1.0.0

3 years ago

0.2.1

3 years ago

1.0.3

3 years ago

0.2.0

3 years ago

0.0.1

3 years ago