@webqit/oohtml 2.1.54 → 2.1.55

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/README.md CHANGED
@@ -5,25 +5,27 @@
5
5
  [![bundle][bundle-src]][bundle-href]
6
6
  [![License][license-src]][license-href]
7
7
 
8
- **[Overview](#an-overview) • [Polyfill](#the-polyfill) • [Design Discussion](#design-discussion) • [Getting Involved](#getting-involved) • [License](#license)**
8
+ **[Overview](#overview) • [Modular HTML](#modular-html) • [HTML Imports](#html-imports) • [Reactive HTML](#reactive-html) • [Polyfill](#polyfill) • [Examples](#examples) • [License](#license)**
9
9
 
10
10
  Object-Oriented HTML (OOHTML) is a set of language features for authoring modular, reusable markup, and for translating that to functional DOM-level objects! Everything comes together as a delightful holistic component architecture for the modern UI!
11
11
 
12
12
  OOHTML is an upcoming proposal!
13
13
 
14
- <!--
15
14
  ## Motivation
16
15
 
16
+ <details><summary>Show</summary>
17
+
17
18
  The web has generally outgrown the idea of a monolith architecture on the UI! But enter HTML; the current authoring experience is one where an author is trying to think out one thing but forced to work out everything, in how the language for the job poses one global scope as the unit of abstraction for styles, scripts and element identifiers — enforcing many global dependencies; inflicting much global thinking!
18
19
 
19
20
  Think too of how authors often have to do half of the work in HTML and half in JS just to have reusable markup!
20
21
 
21
- This project is a proposal for a new standards work that revisits much of the oldish monolith-oriented constraints in HTML that inhibit the idea of a *component* architecture in HTML! The name Object-Oriented HMTL turns out to be more descriptive of the idea than the "component" paradigm!
22
+ This project is a proposal for a new standards work that revisits much of the oldish monolith-oriented constraints in HTML that inhibit the idea of a *component* architecture in HTML!
22
23
 
23
24
  └ [See more in the introductory blog post](https://dev.to/oxharris/the-web-native-equations-1m1p-temp-slug-6661657?preview=ba70ad2c17f05b5761bc74516dbde8c9eff8b581a0420d87334fd9ef6bab9d6e6d3ab6aaf3fe02542bb9e7250d0a88a6df91dae40919aabcc9a07320)<sup>draft</sup>
24
- -->
25
25
 
26
- ## An Overview
26
+ </details>
27
+
28
+ ## Overview
27
29
 
28
30
  OOHTML comes in three sets of features, and the following is an overview. A more detailed documentation for OOHTML is underway in the [project wiki](https://github.com/webqit/oohtml/wiki).
29
31
 
@@ -34,7 +36,7 @@ OOHTML comes in three sets of features, and the following is an overview. A more
34
36
 
35
37
  > **Note** This is documentation for `OOHTML@2.x`. (Looking for [`OOHTML@1.x`](https://github.com/webqit/oohtml/tree/v1.10.4)?)
36
38
 
37
- ### Modular HTML
39
+ ## Modular HTML
38
40
 
39
41
  The first set of features covers authoring objects with self-contained structure, styling and *scripting*! This simply gets identifiers, style sheets and scripts to serve *at the object level* exactly as they do *at the document (object) level*.
40
42
 
@@ -84,7 +86,7 @@ let { styleSheets, scripts } = user; // APIs that are analogous to the document.
84
86
 
85
87
  └ [Modular HTML concepts](#)
86
88
 
87
- ### HTML Imports
89
+ ## HTML Imports
88
90
 
89
91
  The next set of features covers *templating and reusing objects* - in both *declarative* and *programmatic* terms! It extends the language with the *module identifier* attribute `def`, and introduces a complementary new `<import>` element, and has everything working together as a real-time module system.
90
92
 
@@ -363,7 +365,7 @@ document.querySelector('div').import('#fragment2', divElement => {
363
365
 
364
366
  └ [HTML Imports concepts](#)
365
367
 
366
- ### Reactive HTML
368
+ ## Reactive HTML
367
369
 
368
370
  The last set of features covers the concept of "state", "bindings", and "reactivity" for those objects at the DOM level - in the most exciting form of the terms and as an upgrade path! This comes factored into the design as something intrinsic to the problem.
369
371
 
@@ -476,14 +478,160 @@ Observer.set(element, 'liveProperty'); // Live expressions rerun
476
478
 
477
479
  └ [Reactive HTML concepts](#)
478
480
 
479
- ### Put Together
481
+ ## Polyfill
482
+
483
+ OOHTML is being developed as something to be used today - via a polyfill.
484
+
485
+ <details><summary>Load from a CDN<br>
486
+ └───────── <a href="https://bundlephobia.com/result?p=@webqit/oohtml"><img align="right" src="https://img.shields.io/bundlephobia/minzip/@webqit/oohtml?label=&style=flat&colorB=black"></a></summary>
487
+
488
+ ```html
489
+ <script src="https://unpkg.com/@webqit/oohtml/dist/main.js"></script>
490
+ ```
491
+
492
+ └ This is to be placed early on in the document and should be a classic script without any `defer` or `async` directives!
493
+
494
+ <details><summary>Want Async Loading?</summary>
495
+
496
+ If you must load the script "async", one little trade-off has to be made for `<script scoped>` and `<script stateful>` elements to have them ignored by the browser until the polyfill comes picking them up: *employing a custom MIME type in place of the standard `text/javascript` and `module` types*, in which case, a `<meta name="scoped-js">` element is used to configure the polyfill to honor the custom MIME type:
497
+
498
+ ```html
499
+ <head>
500
+ <meta name="scoped-js" content="script.mimeType=some-mime">
501
+ <script async src="https://unpkg.com/@webqit/oohtml/dist/main.js"></script>
502
+ </head>
503
+ <body>
504
+ <script type="some-mime" scoped>
505
+ console.log(this); // body
506
+ </script>
507
+ </body>
508
+ ```
509
+
510
+ The custom MIME type strategy also comes in as a "fix" for when in a browser or other runtime where the polyfill is not able to intercept `<script scoped>` and `<script stateful>` elements ahead of the runtime - e.g. where...
480
511
 
481
- All of OOHTML brings to the platform much of the modern UI development paradigms that community-based tools have long encoded, and that just opens up new ways to leverage the web platform and bank less on abstractions! Here are a few examples in the wide range of use cases these features cover.
512
+ ```html
513
+ <body>
514
+ <script scoped>
515
+ console.log(this); // body
516
+ </script>
517
+ </body>
518
+ ```
482
519
 
483
- **--> Example 1:** The following is how something you could call a Single Page Application ([SPA](https://en.wikipedia.org/wiki/Single-page_application)) could be made - with zero tooling:
520
+ ...still gives the `window` object in the console.
521
+
522
+ </details>
523
+
524
+ For the Scoped Styles feature, you'd also need something like the [samthor/scoped](https://github.com/samthor/scoped) polyfill (more details below):
525
+
526
+ ```html
527
+ <head>
528
+ <script src="https://unpkg.com/style-scoped/scoped.min.js"></script>
529
+ </head>
530
+ ```
531
+
532
+ </details>
533
+
534
+ <details><summary>Extended usage concepts</summary>
535
+
536
+ To use the polyfill on server-side DOM instances as made possible by libraries like [jsdom](https://github.com/jsdom/jsdom), simply install and initialize the library `@webqit/oohtml` with the DOM instance:
537
+
538
+ ```bash
539
+ npm i @webqit/oohtml
540
+ ```
541
+
542
+ ```js
543
+ // Import
544
+ import init from '@webqit/oohtml';
545
+
546
+ // Initialize the lib
547
+ init.call( window[, options = {} ]);
548
+ ```
549
+
550
+ But all things "SSR" for OOHTML are best left to the [`@webqit/oohtml-ssr`](https://github.com/webqit/oohtml-ssr) package!
551
+
552
+ Also, if you'll be going ahead to build a real app to see OOHTML in action, you may want to consider also using:
553
+
554
+ + the [`@webqit/oohtml-cli`](https://github.com/webqit/oohtml-cli) package for operating a file-based templating system.
555
+
556
+ + the modest, OOHTML-based [Webflo](https://github.com/webqit/webflo) framework to greatly streamline your application development process!
557
+
558
+ </details>
559
+
560
+ <details><summary>Implementation Notes</summary>
561
+
562
+ + **Scoped/Stateful Scripts**. This feature is an extension of [Stateful JS](https://github.com/webqit/stateful-js). The default OOHTML build is based on the [Stateful JS Lite APIs](https://github.com/webqit/stateful-js#stateful-js-lite) and this means that `<script stateful></script>` and `<script scoped></script>` elements are parsed "asynchronously", in the same timing as `<script type="module"></script>`!
563
+
564
+ This timing works perfectly generally, but if you have a requirment to have classic scripts follow their [native synchronous timing](https://html.spec.whatwg.org/multipage/parsing.html#scripts-that-modify-the-page-as-it-is-being-parsed), then you need to the *realtime* OOHTML build:
565
+
566
+ ```html
567
+ <head>
568
+ <script src="https://unpkg.com/@webqit/oohtml/dist/main.realtime.js"></script>
569
+ </head>
570
+ ```
571
+
572
+ + **Scoped CSS**. This feature is only in "concept" implementation and doesn't work right now as is. The current implementation simply wraps `<style scoped>` blocks in an `@scope {}` block - which itself isn't supported in any browser. To try this "concept" implementation, set the `style.strategy` config to `@scope`:
573
+
574
+ ```html
575
+ <head>
576
+ <meta name="scoped-css" content="style.strategy=@scope"> <!-- Must come before the polyfil -->
577
+ <script src="https://unpkg.com/@webqit/oohtml/dist/main.js"></script>
578
+ <head>
579
+ ```
580
+
581
+ Now the following `<style scoped>`...
582
+
583
+ ```html
584
+ <style scoped>
585
+ h2 { color: red; }
586
+ </style>
587
+ ```
588
+
589
+ ...will be wrapped to something like:
590
+
591
+ ```html
592
+ <style ref="scoped8eff" scoped>
593
+ @scope from (:has(> style[ref="scoped8eff"])) {
594
+ h2 { color: red; }
595
+ }
596
+ </style>
597
+ ```
598
+
599
+ A working implementation may be coming soon, but in the meantime, you could try one of the polyfills for `<style scoped>` out there; e.g. [samthor/scoped](https://github.com/samthor/scoped):
600
+
601
+ ```html
602
+ <script src="https://unpkg.com/style-scoped/scoped.min.js"></script>
603
+ ```
604
+
605
+ + **HTML Imports**. The attribute names for exposing reusable modules and for referencing them - the `def` and `ref` keywords, respectively - aren't finalized. While the principle of operation remains, these attributes may be renamed in subsequent iterations. But the polyfill is designed to always defer to any syntax that has been explicitly specified using a meta tag. Here's an example:
606
+
607
+ ```html
608
+ <head>
609
+ <meta name="html-imports" content="template.attr.moduledef=def; template.attr.fragmentdef=def; import.attr.moduleref=ref;"> <!-- Must come before the polyfil -->
610
+ <script src="https://unpkg.com/@webqit/oohtml/dist/main.js"></script>
611
+ <head>
612
+ ```
613
+
614
+ Now, even when the default attribute names change, your `def` and `ref` implementation will still work:
615
+
616
+ </details>
617
+
618
+ ## Examples
619
+
620
+ Here are a few examples in the wide range of use cases these features cover.
621
+
622
+ + [Example 1: *Single Page Application*](#example-1-single-page-application)
623
+ + [Example 2: *Multi-Level Namespacing*](#example-2-multi-level-namespacing)
624
+ + [Example 3: *Dynamic Shadow DOM*](#example-3-dynamic-shadow-dom)
625
+ + [Example 4: *List Items*](#example-4-list-items)
626
+
627
+ ### Example 1: *Single Page Application*
628
+
629
+ The following is how something you could call a Single Page Application ([SPA](https://en.wikipedia.org/wiki/Single-page_application)) could be made - with zero tooling:
484
630
 
485
631
  └ *First, two components that are themselves analogous to a Single File Component ([SFC](https://vuejs.org/guide/scaling-up/sfc.html))*:
486
632
 
633
+ <details><summary>Code</summary>
634
+
487
635
  ```html
488
636
  <template def="pages">
489
637
 
@@ -517,8 +665,12 @@ All of OOHTML brings to the platform much of the modern UI development paradigms
517
665
  </template>
518
666
  ```
519
667
 
668
+ </details>
669
+
520
670
  └ *Then a 2-line router that alternates the view based on the URL hash*:
521
671
 
672
+ <details><summary>Code</summary>
673
+
522
674
  ```html
523
675
  <body importscontext="/pages/home">
524
676
 
@@ -534,9 +686,13 @@ All of OOHTML brings to the platform much of the modern UI development paradigms
534
686
  </body>
535
687
  ```
536
688
 
537
- **--> Example 2:** The following is a Listbox component lifted directly from the [ARIA Authoring Practices Guide (APG)](https://www.w3.org/WAI/ARIA/apg/patterns/listbox/examples/listbox-grouped/#sc_label) but with IDs effectively "contained" at different levels within the component using the `namespace` attribute.
689
+ </details>
690
+
691
+ ### Example 2: *Multi-Level Namespacing*
538
692
 
539
- *A Listbox with namespaced IDs*:
693
+ The following is a Listbox component lifted directly from the [ARIA Authoring Practices Guide (APG)](https://www.w3.org/WAI/ARIA/apg/patterns/listbox/examples/listbox-grouped/#sc_label) but with IDs effectively "contained" at different levels within the component using the `namespace` attribute.
694
+
695
+ <details><summary>Code</summary>
540
696
 
541
697
  ```html
542
698
  <div namespace class="listbox-area">
@@ -601,10 +757,16 @@ All of OOHTML brings to the platform much of the modern UI development paradigms
601
757
  </div>
602
758
  ```
603
759
 
604
- **--> Example 3:** The following is a custom element that derives its Shadow DOM from an imported `<tenplate>` element. The idea is to have different Shadow DOM layouts defined and let the "usage" context decide which variant is imported!
760
+ </details>
761
+
762
+ ### Example 3: *Dynamic Shadow DOM*
763
+
764
+ The following is a custom element that derives its Shadow DOM from an imported `<tenplate>` element. The idea is to have different Shadow DOM layouts defined and let the "usage" context decide which variant is imported!
605
765
 
606
766
  └ *First, two layout options defined for the Shadow DOM*:
607
767
 
768
+ <details><summary>Code</summary>
769
+
608
770
  ```html
609
771
  <template def="vendor1">
610
772
 
@@ -623,8 +785,12 @@ All of OOHTML brings to the platform much of the modern UI development paradigms
623
785
  </template>
624
786
  ```
625
787
 
788
+ </details>
789
+
626
790
  └ *Next, the Shadow DOM creation that imports its layout from context*:
627
791
 
792
+ <details><summary>Code</summary>
793
+
628
794
  ```js
629
795
  customElements.define('magic-button', class extends HTMLElement {
630
796
  connectedCallback() {
@@ -636,8 +802,12 @@ customElements.define('magic-button', class extends HTMLElement {
636
802
  });
637
803
  ```
638
804
 
805
+ </details>
806
+
639
807
  └ *Then, the part where we just drop the component in "layout" contexts*:
640
808
 
809
+ <details><summary>Code</summary>
810
+
641
811
  ```html
642
812
  <div contextname="vendor1" importscontext="/vendor1/components-layout1">
643
813
 
@@ -650,9 +820,13 @@ customElements.define('magic-button', class extends HTMLElement {
650
820
  </div>
651
821
  ```
652
822
 
653
- **--> Example 4:** The following is a "component" that derives its list items and other reusable snippets from "scoped" `<tenplate>` elements. The idea is to have a "self-contained" component that's all markup-based, not class-based!
823
+ </details>
824
+
825
+ ### Example 4: *List Items*
654
826
 
655
- *A list component with scoped module system*:
827
+ The following is a "component" that derives its list items and other reusable snippets from "scoped" `<tenplate>` elements. The idea is to have a "self-contained" component that's all markup-based, not class-based!
828
+
829
+ <details><summary>Code</summary>
656
830
 
657
831
  ```html
658
832
  <div namespace>
@@ -681,148 +855,8 @@ customElements.define('magic-button', class extends HTMLElement {
681
855
  </div>
682
856
  ```
683
857
 
684
- ## The Polyfill
685
-
686
- OOHTML is being developed as something to be used today - via a polyfill. This has been helping to facilitate the "release - iterations" loop and its overall evolution.
687
-
688
- The polyfill can be loaded from the `unpkg.com` CDN, and should be placed early on in the document - before any OOHTML-specific features are used - and should be a classic script without any `defer` or `async` directives:
689
-
690
- ```html
691
- <head>
692
- <script src="https://unpkg.com/@webqit/oohtml/dist/main.js"></script>
693
- </head>
694
- ```
695
-
696
- > 22.5 kB min + gz | 77.5 KB min [↗](https://bundlephobia.com/package/@webqit/oohtml@2.1.45)
697
-
698
- <details><summary>
699
- Extended usage concepts
700
- </summary>
701
-
702
- If you must load the script "async", one little trade-off has to be made for `<script scoped>` and `<script stateful>` elements to have them ignored by the browser until the polyfill comes picking them up: *employing a custom MIME type in place of the standard `text/javascript` and `module` types*, in which case, a `<meta name="scoped-js">` element is used to configure the polyfill to honor the custom MIME type:
703
-
704
- ```html
705
- <head>
706
- <meta name="scoped-js" content="script.mimeType=some-mime">
707
- <script async src="https://unpkg.com/@webqit/oohtml/dist/main.js"></script>
708
- </head>
709
- <body>
710
- <script type="some-mime" scoped>
711
- console.log(this); // body
712
- </script>
713
- </body>
714
- ```
715
-
716
- The custom MIME type strategy also comes in as a "fix" for when in a browser or other runtime where the polyfill is not able to intercept `<script scoped>` and `<script stateful>` elements ahead of the runtime - e.g. where...
717
-
718
- ```html
719
- <body>
720
- <script scoped>
721
- console.log(this); // body
722
- </script>
723
- </body>
724
- ```
725
-
726
- ...still gives the `window` object in the console.
727
-
728
- To use the polyfill on server-side DOM instances as made possible by libraries like [jsdom](https://github.com/jsdom/jsdom), simply install and initialize the library `@webqit/oohtml` with the DOM instance:
729
-
730
- ```bash
731
- npm i @webqit/oohtml
732
- ```
733
-
734
- ```js
735
- // Import
736
- import init from '@webqit/oohtml';
737
-
738
- // Initialize the lib
739
- init.call( window[, options = {} ]);
740
- ```
741
-
742
- But all things "SSR" for OOHTML are best left to the [`@webqit/oohtml-ssr`](https://github.com/webqit/oohtml-ssr) package!
743
-
744
- Also, if you'll be going ahead to build a real world app to see OOHTML in action, you may want to consider also using:
745
-
746
- + the [`@webqit/oohtml-cli`](https://github.com/webqit/oohtml-cli) package for operating a file-based templating system.
747
-
748
- + the modest, OOHTML-based [Webflo](https://github.com/webqit/webflo) framework to greatly streamline your application development process!
749
-
750
- </details>
751
-
752
- <details><summary>
753
- Implementation Notes
754
- </summary>
755
-
756
- Here are some performance-specific notes for this polyfill:
757
-
758
- + By default, the Stateful JS compiler (44.31 KB min+compressed | 157KB min) is excluded from the polyfill build and fetched separately on demand - on the first encounter with a Stateful Script. This is loaded into a [Web Worker](https://developer.mozilla.org/en-US/docs/Web/API/Web_Workers_API/Using_web_workers) and all compilations are able to happen off the main thread! This ensures near-zero cost to your application loading and runtime performance!
759
-
760
- Note that this lazy-loading approach means that all Stateful Scripts will behave "async" just like module scripts; i.e. scripts are defered until the compiler has been loaded. In other words, the following two scripts will have the same timing semantics:
761
-
762
- ```html
763
- <script stateful></script>
764
- <script type="module" stateful></script>
765
- ```
766
-
767
- This isn't necessarily bad unless there is a requirment to have classic scripts follow their [native synchronous timing](https://html.spec.whatwg.org/multipage/parsing.html#scripts-that-modify-the-page-as-it-is-being-parsed), in which case the Stateful JS compiler will need to be explicitly and synchronously loaded ahead of any encounter with classic Stateful Scripts:
768
-
769
- ```html
770
- <head>
771
- <script src="https://unpkg.com/@webqit/stateful-js/dist/compiler.js"></script> <!-- Must come before the polyfil -->
772
- <script src="https://unpkg.com/@webqit/oohtml/dist/main.js"></script>
773
- </head>
774
- ```
775
-
776
- + Whether loaded lazily or eagerly, the compiler also factors in additional optimizations. For example, identical scripts are handled only first time, and only ever have one Stateful JS instance!
777
-
778
- Here are other notes:
779
-
780
- + **Scoped CSS**. This feature is only in "concept" implementation and doesn't work right now as is. The current implementation simply wraps `<style scoped>` blocks in an `@scope {}` block - which itself isn't supported in any browser. To try this "concept" implementation, set the `style.strategy` config to `@scope`:
781
-
782
- ```html
783
- <head>
784
- <meta name="scoped-css" content="style.strategy=@scope"> <!-- Must come before the polyfil -->
785
- <script src="https://unpkg.com/@webqit/oohtml/dist/main.js"></script>
786
- <head>
787
- ```
788
-
789
- Now the following `<style scoped>`...
790
-
791
- ```html
792
- <style scoped>
793
- h2 { color: red; }
794
- </style>
795
- ```
796
-
797
- ...will be wrapped to something like:
798
-
799
- ```html
800
- <style ref="scoped8eff" scoped>
801
- @scope from (:has(> style[ref="scoped8eff"])) {
802
- h2 { color: red; }
803
- }
804
- </style>
805
- ```
806
-
807
- A working implementation may be coming soon, but in the meantime, you could try one of the polyfills for `<style scoped>` out there; e.g. [samthor/scoped](https://github.com/samthor/scoped).
808
-
809
- + **HTML Imports**. The attribute names for exposing reusable modules and for referencing them - the `def` and `ref` keywords, respectively - aren't finalized. While the principle of operation remains, these attributes may be renamed in subsequent iterations. But the polyfill is designed to always defer to any syntax that has been explicitly specified using a meta tag. Here's an example:
810
-
811
- ```html
812
- <head>
813
- <meta name="html-imports" content="template.attr.moduledef=def; template.attr.fragmentdef=def; import.attr.moduleref=ref;"> <!-- Must come before the polyfil -->
814
- <script src="https://unpkg.com/@webqit/oohtml/dist/main.js"></script>
815
- <head>
816
- ```
817
-
818
- Now, even when the default attribute names change, your `def` and `ref` implementation will still work:
819
-
820
858
  </details>
821
859
 
822
- ## Design Discussion
823
-
824
- *[TODO]*
825
-
826
860
  ## Getting Involved
827
861
 
828
862
  All forms of contributions are welcome at this time. For example, syntax and other implementation details are all up for discussion. Also, help is needed with more formal documentation. And here are specific links: