@blockquote-web-components/blockquote-controller-context-meta 1.2.8 → 1.3.0
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 +75 -119
- package/package.json +10 -4
- package/src/BaseContextMetaElement.js +30 -127
- package/src/BlockquoteControllerContextMeta.d.ts +1 -1
- package/src/BlockquoteControllerContextMeta.js +5 -5
- package/src/directives/cache-context-meta-provider.js +15 -0
- package/src/directives/context-meta-provider.js +94 -0
- package/src/index.js +5 -0
package/README.md
CHANGED
|
@@ -1,133 +1,45 @@
|
|
|
1
1
|

|
|
2
2
|
|
|
3
|
-
`BaseContextMetaElement`
|
|
4
|
-
|
|
5
|
-
> [Is it possible to make normal dom elements context providers?](https://github.com/lit/lit/discussions/4690)
|
|
3
|
+
`BaseContextMetaElement` simulates the behavior of a `div` using ARIA roles,
|
|
4
|
+
preserving standard HTML behaviors while enhancing functionality.
|
|
6
5
|
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
### Demo
|
|
6
|
+
## Demo
|
|
10
7
|
|
|
11
8
|
[](https://stackblitz.com/github/oscarmarina/flow-element)
|
|
12
9
|
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
```js
|
|
18
|
-
static styles = [
|
|
19
|
-
css`
|
|
20
|
-
:host {
|
|
21
|
-
display: block;
|
|
22
|
-
}
|
|
23
|
-
:host([hidden]),
|
|
24
|
-
[hidden] {
|
|
25
|
-
display: none !important;
|
|
26
|
-
}
|
|
27
|
-
`,
|
|
28
|
-
];
|
|
29
|
-
```
|
|
30
|
-
|
|
31
|
-
2. The initOrGetContextProvider method allows setting up a context consumer on the element. It creates a new BlockquoteControllerContextMeta if one does not already exist.
|
|
32
|
-
```js
|
|
33
|
-
initOrGetContextProvider(contextOrOptions = contextMetaSymbol) {
|
|
34
|
-
const ctx =
|
|
35
|
-
contextOrOptions?.context !== undefined
|
|
36
|
-
? { ...contextOrOptions }
|
|
37
|
-
: { context: contextOrOptions };
|
|
38
|
-
|
|
39
|
-
if (!this.#controllerBaseContextMeta) {
|
|
40
|
-
this.#controllerBaseContextMeta = new BlockquoteControllerContextMeta(this, ctx);
|
|
41
|
-
}
|
|
42
|
-
return this.#controllerBaseContextMeta;
|
|
43
|
-
}
|
|
44
|
-
```
|
|
45
|
-
|
|
46
|
-
3. Set a default role of 'presentation' to ensure it behaves semantically like a non-interactive container.
|
|
47
|
-
```js
|
|
48
|
-
connectedCallback() {
|
|
49
|
-
super.connectedCallback?.();
|
|
50
|
-
Object.assign(this, { role: this.role ?? 'presentation' });
|
|
51
|
-
}
|
|
52
|
-
```
|
|
53
|
-
|
|
54
|
-
4. The render method includes a <slot>, which allows this element to be a flexible container for any child content, mimicking the behavior of a [flow element](https://developer.mozilla.org/en-US/docs/Web/HTML/Content_categories#flow_content).
|
|
55
|
-
```js
|
|
56
|
-
render() {
|
|
57
|
-
return html`<slot></slot>`;
|
|
58
|
-
}
|
|
59
|
-
```
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
### Usage Example: FlownElement
|
|
63
|
-
To demonstrate the utility of BaseContextMetaElement, let's create a derived class called FlownElement:
|
|
64
|
-
|
|
65
|
-
1. Define Properties: The surface property is declared with reflection, allowing it to influence rendering and context behavior dynamically.
|
|
66
|
-
```js
|
|
67
|
-
static properties = {
|
|
68
|
-
surface: { reflect: true },
|
|
69
|
-
};
|
|
70
|
-
```
|
|
71
|
-
|
|
72
|
-
2. Set Context on Construction: The constructor calls initOrGetContextProvider with a specific context, enabling the element to participate in the context API from its inception.
|
|
73
|
-
```js
|
|
74
|
-
constructor() {
|
|
75
|
-
super();
|
|
76
|
-
this.surface = undefined;
|
|
77
|
-
this.flowController = this.initOrGetContextProvider(consumerContext);
|
|
78
|
-
}
|
|
79
|
-
```
|
|
80
|
-
|
|
81
|
-
3. Update Context Values: The willUpdate lifecycle method updates the context value whenever the surface property changes, ensuring context-sensitive operations react appropriately.
|
|
82
|
-
```js
|
|
83
|
-
willUpdate(props) {
|
|
84
|
-
super.willUpdate?.(props);
|
|
85
|
-
if (props.has('surface')) {
|
|
86
|
-
this.flowController?.setValue(this.surface);
|
|
87
|
-
}
|
|
88
|
-
}
|
|
89
|
-
```
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
### Usage Example:
|
|
93
|
-
Here's how you might use the FlownElement in your HTML:
|
|
94
|
-
|
|
95
|
-
```html
|
|
96
|
-
<flow-element surface="dim">
|
|
97
|
-
<!-- Child content that can consume context from this provider -->
|
|
98
|
-
</flow-element>
|
|
99
|
-
```
|
|
10
|
+
## Features
|
|
11
|
+
- Acts as a structural element that follows HTML flow content rules.
|
|
12
|
+
- Provides a default ARIA role (`none`) to avoid unintended semantics.
|
|
13
|
+
- Can be used as a wrapper for contextual metadata.
|
|
100
14
|
|
|
101
|
-
|
|
15
|
+
## Accessibility
|
|
16
|
+
By default, `BaseContextMetaElement` [assigns the role="none"](https://github.com/w3c/aria/pull/2383),
|
|
17
|
+
ensuring that it does not introduce unintended semantics in assistive technologies.
|
|
18
|
+
This behavior can be overridden by explicitly setting a different role.
|
|
102
19
|
|
|
20
|
+
**Related:** [ARIA Structural Roles](https://www.w3.org/WAI/ARIA/apg/practices/structural-roles/#allstructuralrolesandtheirhtmlequivalents)
|
|
103
21
|
|
|
104
|
-
|
|
22
|
+
> Inspired by the discussion: [Is it possible to make normal DOM elements context providers?](https://github.com/lit/lit/discussions/4690)
|
|
23
|
+
**See Also:** [contextmeta provider directive](https://github.com/oscarmarina/blockquote-web-components/tree/main/packages/controllers/blockquote-controller-context-meta/src/directives/context-meta-provider.js)
|
|
105
24
|
|
|
106
|
-
|
|
25
|
+
With this setup, `BaseContextMetaElement` behaves like a [flow element](https://developer.mozilla.org/en-US/docs/Web/HTML/Content_categories#flow_content).
|
|
107
26
|
|
|
108
|
-
##### Methods
|
|
109
27
|
|
|
110
|
-
|
|
111
|
-
| -------------------------- | ------- | ------------------------------------------------------------ | ------------------------------------ | --------------------------------- | -------------- |
|
|
112
|
-
| `initOrGetContextProvider` | | Initializes or returns the existing context meta controller. | `contextOrOptions: string \| Object` | `BlockquoteControllerContextMeta` | |
|
|
113
|
-
|
|
114
|
-
<details><summary>Private API</summary>
|
|
28
|
+
<hr>
|
|
115
29
|
|
|
116
|
-
##### Fields
|
|
117
30
|
|
|
118
|
-
|
|
119
|
-
| ---------------------------- | ------- | ---------------------------------------------- | ----------- | --------------------------------------- | -------------- |
|
|
120
|
-
| `#controllerBaseContextMeta` | private | `BlockquoteControllerContextMeta \| undefined` | `undefined` | Stores the context controller instance. | |
|
|
31
|
+
### `src/BaseContextMetaElement.js`:
|
|
121
32
|
|
|
122
|
-
|
|
33
|
+
#### class: `BaseContextMetaElement`, `base-context-meta`
|
|
123
34
|
|
|
124
35
|
<hr/>
|
|
125
36
|
|
|
126
37
|
#### Exports
|
|
127
38
|
|
|
128
|
-
| Kind
|
|
129
|
-
|
|
|
130
|
-
| `js`
|
|
39
|
+
| Kind | Name | Declaration | Module | Package |
|
|
40
|
+
| --------------------------- | ------------------------ | ---------------------- | ----------------------------- | ------- |
|
|
41
|
+
| `js` | `BaseContextMetaElement` | BaseContextMetaElement | src/BaseContextMetaElement.js | |
|
|
42
|
+
| `custom-element-definition` | `base-context-meta` | BaseContextMetaElement | src/BaseContextMetaElement.js | |
|
|
131
43
|
|
|
132
44
|

|
|
133
45
|
|
|
@@ -177,7 +89,7 @@ export class ProviderEl extends LitElement {
|
|
|
177
89
|
constructor() {
|
|
178
90
|
super();
|
|
179
91
|
this._provider = new BlockquoteControllerContextMeta(this, {
|
|
180
|
-
context:
|
|
92
|
+
context: Symbol.for('contextKey')
|
|
181
93
|
});
|
|
182
94
|
|
|
183
95
|
this.data = 'Initial';
|
|
@@ -204,7 +116,7 @@ customElements.define('provider-el', ProviderEl);
|
|
|
204
116
|
|
|
205
117
|
export class ConsumerEl extends LitElement {
|
|
206
118
|
_consumer = new BlockquoteControllerContextMeta(this, {
|
|
207
|
-
context:
|
|
119
|
+
context: Symbol.for('contextKey')
|
|
208
120
|
callback: (v) => {
|
|
209
121
|
this.setAttribute('data-callback', v);
|
|
210
122
|
},
|
|
@@ -256,9 +168,9 @@ customElements.define('consumer-el', ConsumerEl);
|
|
|
256
168
|
|
|
257
169
|
#### Variables
|
|
258
170
|
|
|
259
|
-
| Name | Description | Type
|
|
260
|
-
| ------------------- | ----------- |
|
|
261
|
-
| `contextMetaSymbol` | |
|
|
171
|
+
| Name | Description | Type |
|
|
172
|
+
| ------------------- | ----------- | ---- |
|
|
173
|
+
| `contextMetaSymbol` | | |
|
|
262
174
|
|
|
263
175
|
<hr/>
|
|
264
176
|
|
|
@@ -273,7 +185,51 @@ customElements.define('consumer-el', ConsumerEl);
|
|
|
273
185
|
|
|
274
186
|
#### Exports
|
|
275
187
|
|
|
276
|
-
| Kind | Name | Declaration | Module
|
|
277
|
-
| ---- | --------------------------------- | ------------------------------- |
|
|
278
|
-
| `js` | `BlockquoteControllerContextMeta` | BlockquoteControllerContextMeta | ./BlockquoteControllerContextMeta.js
|
|
279
|
-
| `js` | `BaseContextMetaElement` | BaseContextMetaElement | ./BaseContextMetaElement.js
|
|
188
|
+
| Kind | Name | Declaration | Module | Package |
|
|
189
|
+
| ---- | --------------------------------- | ------------------------------- | ------------------------------------------- | ------- |
|
|
190
|
+
| `js` | `BlockquoteControllerContextMeta` | BlockquoteControllerContextMeta | ./BlockquoteControllerContextMeta.js | |
|
|
191
|
+
| `js` | `BaseContextMetaElement` | BaseContextMetaElement | ./BaseContextMetaElement.js | |
|
|
192
|
+
| `js` | `contextMetaProvider` | contextMetaProvider | ./directives/context-meta-provider.js | |
|
|
193
|
+
| `js` | `cacheContextMetaProvider` | cacheContextMetaProvider | ./directives/cache-context-meta-provider.js | |
|
|
194
|
+
| `js` | `contextMetaKeyProvider` | contextMetaKeyProvider | ./directives/cache-context-meta-provider.js | |
|
|
195
|
+
|
|
196
|
+
### `src/directives/cache-context-meta-provider.js`:
|
|
197
|
+
|
|
198
|
+
#### Variables
|
|
199
|
+
|
|
200
|
+
| Name | Description | Type |
|
|
201
|
+
| ------------------------ | ----------- | ---- |
|
|
202
|
+
| `contextMetaKeyProvider` | | |
|
|
203
|
+
|
|
204
|
+
<hr/>
|
|
205
|
+
|
|
206
|
+
#### Functions
|
|
207
|
+
|
|
208
|
+
| Name | Description | Parameters | Return |
|
|
209
|
+
| -------------------------- | ----------- | --------------------------- | ------ |
|
|
210
|
+
| `cacheContextMetaProvider` | | `element, contextOrOptions` | |
|
|
211
|
+
|
|
212
|
+
<hr/>
|
|
213
|
+
|
|
214
|
+
#### Exports
|
|
215
|
+
|
|
216
|
+
| Kind | Name | Declaration | Module | Package |
|
|
217
|
+
| ---- | -------------------------- | ------------------------ | --------------------------------------------- | ------- |
|
|
218
|
+
| `js` | `contextMetaKeyProvider` | contextMetaKeyProvider | src/directives/cache-context-meta-provider.js | |
|
|
219
|
+
| `js` | `cacheContextMetaProvider` | cacheContextMetaProvider | src/directives/cache-context-meta-provider.js | |
|
|
220
|
+
|
|
221
|
+
### `src/directives/context-meta-provider.js`:
|
|
222
|
+
|
|
223
|
+
#### Variables
|
|
224
|
+
|
|
225
|
+
| Name | Description | Type |
|
|
226
|
+
| --------------------- | ----------- | ---- |
|
|
227
|
+
| `contextMetaProvider` | | |
|
|
228
|
+
|
|
229
|
+
<hr/>
|
|
230
|
+
|
|
231
|
+
#### Exports
|
|
232
|
+
|
|
233
|
+
| Kind | Name | Declaration | Module | Package |
|
|
234
|
+
| ---- | --------------------- | ------------------- | --------------------------------------- | ------- |
|
|
235
|
+
| `js` | `contextMetaProvider` | contextMetaProvider | src/directives/context-meta-provider.js | |
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@blockquote-web-components/blockquote-controller-context-meta",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.3.0",
|
|
4
4
|
"description": "Webcomponent blockquote-controller-context-meta following open-wc recommendations",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"lit",
|
|
@@ -20,6 +20,12 @@
|
|
|
20
20
|
"./BlockquoteControllerContextMeta.js": {
|
|
21
21
|
"default": "./src/BlockquoteControllerContextMeta.js"
|
|
22
22
|
},
|
|
23
|
+
"./BaseContextMetaElement.js": {
|
|
24
|
+
"default": "./src/BaseContextMetaElement.js"
|
|
25
|
+
},
|
|
26
|
+
"./contextMetaProvider.js": {
|
|
27
|
+
"default": "./directives/context-meta-provider.js"
|
|
28
|
+
},
|
|
23
29
|
"./index.js": {
|
|
24
30
|
"default": "./src/index.js"
|
|
25
31
|
}
|
|
@@ -115,12 +121,12 @@
|
|
|
115
121
|
"lit": "^3.2.1"
|
|
116
122
|
},
|
|
117
123
|
"devDependencies": {
|
|
118
|
-
"@blockquote-web-components/blockquote-base-common-dev-dependencies": "^1.11.
|
|
119
|
-
"@blockquote-web-components/blockquote-base-embedded-webview": "^1.12.
|
|
124
|
+
"@blockquote-web-components/blockquote-base-common-dev-dependencies": "^1.11.2",
|
|
125
|
+
"@blockquote-web-components/blockquote-base-embedded-webview": "^1.12.9"
|
|
120
126
|
},
|
|
121
127
|
"publishConfig": {
|
|
122
128
|
"access": "public"
|
|
123
129
|
},
|
|
124
130
|
"customElements": "custom-elements.json",
|
|
125
|
-
"gitHead": "
|
|
131
|
+
"gitHead": "9a325725a904f541664565dd720f4bb6b2f0fa05"
|
|
126
132
|
}
|
|
@@ -1,150 +1,51 @@
|
|
|
1
1
|
import {LitElement, html, css} from 'lit';
|
|
2
|
-
|
|
3
|
-
BlockquoteControllerContextMeta,
|
|
4
|
-
contextMetaSymbol,
|
|
5
|
-
} from './BlockquoteControllerContextMeta.js';
|
|
2
|
+
|
|
6
3
|
/**
|
|
7
4
|
* 
|
|
8
5
|
*
|
|
9
|
-
* `BaseContextMetaElement`
|
|
10
|
-
*
|
|
11
|
-
* > [Is it possible to make normal dom elements context providers?](https://github.com/lit/lit/discussions/4690)
|
|
12
|
-
*
|
|
13
|
-
* <hr>
|
|
6
|
+
* `BaseContextMetaElement` simulates the behavior of a `div` using ARIA roles,
|
|
7
|
+
* preserving standard HTML behaviors while enhancing functionality.
|
|
14
8
|
*
|
|
15
|
-
*
|
|
9
|
+
* ## Demo
|
|
16
10
|
*
|
|
17
11
|
* [](https://stackblitz.com/github/oscarmarina/flow-element)
|
|
18
12
|
*
|
|
19
|
-
*
|
|
20
|
-
*
|
|
21
|
-
*
|
|
22
|
-
*
|
|
23
|
-
* ```js
|
|
24
|
-
* static styles = [
|
|
25
|
-
* css`
|
|
26
|
-
* :host {
|
|
27
|
-
* display: block;
|
|
28
|
-
* }
|
|
29
|
-
*
|
|
30
|
-
* :host([hidden]),
|
|
31
|
-
* [hidden] {
|
|
32
|
-
* display: none !important;
|
|
33
|
-
* }
|
|
34
|
-
* `,
|
|
35
|
-
* ];
|
|
36
|
-
* ```
|
|
37
|
-
*
|
|
38
|
-
* 2. The initOrGetContextProvider method allows setting up a context consumer on the element. It creates a new BlockquoteControllerContextMeta if one does not already exist.
|
|
39
|
-
* ```js
|
|
40
|
-
* initOrGetContextProvider(contextOrOptions = contextMetaSymbol) {
|
|
41
|
-
* const ctx =
|
|
42
|
-
* contextOrOptions?.context !== undefined
|
|
43
|
-
* ? { ...contextOrOptions }
|
|
44
|
-
* : { context: contextOrOptions };
|
|
45
|
-
*
|
|
46
|
-
* if (!this.#controllerBaseContextMeta) {
|
|
47
|
-
* this.#controllerBaseContextMeta = new BlockquoteControllerContextMeta(this, ctx);
|
|
48
|
-
* }
|
|
49
|
-
* return this.#controllerBaseContextMeta;
|
|
50
|
-
* }
|
|
51
|
-
* ```
|
|
52
|
-
*
|
|
53
|
-
* 3. Set a default role of 'presentation' to ensure it behaves semantically like a non-interactive container.
|
|
54
|
-
* ```js
|
|
55
|
-
* connectedCallback() {
|
|
56
|
-
* super.connectedCallback?.();
|
|
57
|
-
* Object.assign(this, { role: this.role ?? 'presentation' });
|
|
58
|
-
* }
|
|
59
|
-
* ```
|
|
60
|
-
*
|
|
61
|
-
* 4. The render method includes a <slot>, which allows this element to be a flexible container for any child content, mimicking the behavior of a [flow element](https://developer.mozilla.org/en-US/docs/Web/HTML/Content_categories#flow_content).
|
|
62
|
-
* ```js
|
|
63
|
-
* render() {
|
|
64
|
-
* return html`<slot></slot>`;
|
|
65
|
-
* }
|
|
66
|
-
* ```
|
|
67
|
-
*
|
|
68
|
-
*
|
|
69
|
-
* ### Usage Example: FlownElement
|
|
70
|
-
* To demonstrate the utility of BaseContextMetaElement, let's create a derived class called FlownElement:
|
|
13
|
+
* ## Features
|
|
14
|
+
* - Acts as a structural element that follows HTML flow content rules.
|
|
15
|
+
* - Provides a default ARIA role (`none`) to avoid unintended semantics.
|
|
16
|
+
* - Can be used as a wrapper for contextual metadata.
|
|
71
17
|
*
|
|
72
|
-
*
|
|
73
|
-
*
|
|
74
|
-
*
|
|
75
|
-
*
|
|
76
|
-
* };
|
|
77
|
-
* ```
|
|
18
|
+
* ## Accessibility
|
|
19
|
+
* By default, `BaseContextMetaElement` [assigns the role="none"](https://github.com/w3c/aria/pull/2383),
|
|
20
|
+
* ensuring that it does not introduce unintended semantics in assistive technologies.
|
|
21
|
+
* This behavior can be overridden by explicitly setting a different role.
|
|
78
22
|
*
|
|
79
|
-
*
|
|
80
|
-
* ```js
|
|
81
|
-
* constructor() {
|
|
82
|
-
* super();
|
|
83
|
-
* this.surface = undefined;
|
|
84
|
-
* this.flowController = this.initOrGetContextProvider(consumerContext);
|
|
85
|
-
* }
|
|
86
|
-
* ```
|
|
23
|
+
* **Related:** [ARIA Structural Roles](https://www.w3.org/WAI/ARIA/apg/practices/structural-roles/#allstructuralrolesandtheirhtmlequivalents)
|
|
87
24
|
*
|
|
88
|
-
*
|
|
89
|
-
*
|
|
90
|
-
* willUpdate(props) {
|
|
91
|
-
* super.willUpdate?.(props);
|
|
92
|
-
* if (props.has('surface')) {
|
|
93
|
-
* this.flowController?.setValue(this.surface);
|
|
94
|
-
* }
|
|
95
|
-
* }
|
|
96
|
-
* ```
|
|
25
|
+
* > Inspired by the discussion: [Is it possible to make normal DOM elements context providers?](https://github.com/lit/lit/discussions/4690)
|
|
26
|
+
* **See Also:** [contextmeta provider directive](https://github.com/oscarmarina/blockquote-web-components/tree/main/packages/controllers/blockquote-controller-context-meta/src/directives/context-meta-provider.js)
|
|
97
27
|
*
|
|
28
|
+
* With this setup, `BaseContextMetaElement` behaves like a [flow element](https://developer.mozilla.org/en-US/docs/Web/HTML/Content_categories#flow_content).
|
|
98
29
|
*
|
|
99
|
-
* ### Usage Example:
|
|
100
|
-
* Here's how you might use the FlownElement in your HTML:
|
|
101
30
|
*
|
|
102
|
-
*
|
|
103
|
-
* <flow-element surface="dim">
|
|
104
|
-
* <!-- Child content that can consume context from this provider -->
|
|
105
|
-
* </flow-element>
|
|
106
|
-
* ```
|
|
107
|
-
*
|
|
108
|
-
* With this setup, FlownElement behaves like a [flow element](https://developer.mozilla.org/en-US/docs/Web/HTML/Content_categories#flow_content) but provides the additional benefit of context management via Lit's context API, allowing you to seamlessly integrate context-sensitive behavior without altering the parent element hierarchy.
|
|
31
|
+
* <hr>
|
|
109
32
|
*/
|
|
110
33
|
export class BaseContextMetaElement extends LitElement {
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
*/
|
|
115
|
-
#controllerBaseContextMeta = undefined;
|
|
116
|
-
|
|
117
|
-
static styles = [
|
|
118
|
-
css`
|
|
119
|
-
:host {
|
|
120
|
-
display: block;
|
|
121
|
-
}
|
|
122
|
-
|
|
123
|
-
:host([hidden]),
|
|
124
|
-
[hidden] {
|
|
125
|
-
display: none !important;
|
|
126
|
-
}
|
|
127
|
-
`,
|
|
128
|
-
];
|
|
129
|
-
|
|
130
|
-
/**
|
|
131
|
-
* Initializes or returns the existing context meta controller.
|
|
132
|
-
* @param {string | Object} [contextOrOptions=contextMetaSymbol] - context name.
|
|
133
|
-
* @returns {BlockquoteControllerContextMeta} The instance of the context meta.
|
|
134
|
-
*/
|
|
135
|
-
initOrGetContextProvider(contextOrOptions = contextMetaSymbol) {
|
|
136
|
-
const ctx =
|
|
137
|
-
contextOrOptions?.context !== undefined ? {...contextOrOptions} : {context: contextOrOptions};
|
|
138
|
-
|
|
139
|
-
if (!this.#controllerBaseContextMeta) {
|
|
140
|
-
this.#controllerBaseContextMeta = new BlockquoteControllerContextMeta(this, ctx);
|
|
34
|
+
static styles = css`
|
|
35
|
+
:host {
|
|
36
|
+
display: block;
|
|
141
37
|
}
|
|
142
|
-
|
|
143
|
-
|
|
38
|
+
:host([hidden]),
|
|
39
|
+
[hidden] {
|
|
40
|
+
display: none !important;
|
|
41
|
+
}
|
|
42
|
+
`;
|
|
144
43
|
|
|
145
44
|
connectedCallback() {
|
|
146
45
|
super.connectedCallback?.();
|
|
147
|
-
|
|
46
|
+
if (!this.hasAttribute('role')) {
|
|
47
|
+
this.setAttribute('role', 'none');
|
|
48
|
+
}
|
|
148
49
|
}
|
|
149
50
|
|
|
150
51
|
render() {
|
|
@@ -153,3 +54,5 @@ export class BaseContextMetaElement extends LitElement {
|
|
|
153
54
|
`;
|
|
154
55
|
}
|
|
155
56
|
}
|
|
57
|
+
|
|
58
|
+
customElements.define('base-context-meta', BaseContextMetaElement);
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import {createContext, ContextProvider, ContextConsumer} from '@lit/context';
|
|
2
2
|
|
|
3
|
-
export const contextMetaSymbol = 'context-meta-symbol';
|
|
3
|
+
export const contextMetaSymbol = Symbol.for('context-meta-symbol');
|
|
4
4
|
/**
|
|
5
5
|
* 
|
|
6
6
|
*
|
|
@@ -50,7 +50,7 @@ export const contextMetaSymbol = 'context-meta-symbol';
|
|
|
50
50
|
* constructor() {
|
|
51
51
|
* super();
|
|
52
52
|
* this._provider = new BlockquoteControllerContextMeta(this, {
|
|
53
|
-
* context:
|
|
53
|
+
* context: Symbol.for('contextKey')
|
|
54
54
|
* });
|
|
55
55
|
*
|
|
56
56
|
* this.data = 'Initial';
|
|
@@ -77,7 +77,7 @@ export const contextMetaSymbol = 'context-meta-symbol';
|
|
|
77
77
|
*
|
|
78
78
|
* export class ConsumerEl extends LitElement {
|
|
79
79
|
* _consumer = new BlockquoteControllerContextMeta(this, {
|
|
80
|
-
* context:
|
|
80
|
+
* context: Symbol.for('contextKey')
|
|
81
81
|
* callback: (v) => {
|
|
82
82
|
* this.setAttribute('data-callback', v);
|
|
83
83
|
* },
|
|
@@ -106,13 +106,13 @@ class ContextMeta {
|
|
|
106
106
|
/**
|
|
107
107
|
* @param {import('lit').ReactiveElement} host - The host object.
|
|
108
108
|
* @param {{
|
|
109
|
-
* context?:
|
|
109
|
+
* context?: *,
|
|
110
110
|
* initialValue?: import('@lit/context').ContextType<*>,
|
|
111
111
|
* callback?: (value: import('@lit/context').ContextType<*>, dispose?: () => void) => void
|
|
112
112
|
* }} arg - The arguments for the constructor.
|
|
113
113
|
*/
|
|
114
114
|
constructor(host, {context = contextMetaSymbol, initialValue, callback}) {
|
|
115
|
-
this.context = createContext(
|
|
115
|
+
this.context = createContext(context);
|
|
116
116
|
this.initialValue = initialValue;
|
|
117
117
|
this.callback = callback;
|
|
118
118
|
this.host = host;
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import {BlockquoteControllerContextMeta} from '../BlockquoteControllerContextMeta.js';
|
|
2
|
+
|
|
3
|
+
export const contextMetaKeyProvider = Symbol();
|
|
4
|
+
|
|
5
|
+
export const cacheContextMetaProvider = (element, contextOrOptions) => {
|
|
6
|
+
if (element[contextMetaKeyProvider]) {
|
|
7
|
+
return element[contextMetaKeyProvider];
|
|
8
|
+
}
|
|
9
|
+
|
|
10
|
+
const ctx =
|
|
11
|
+
contextOrOptions?.context !== undefined ? {...contextOrOptions} : {context: contextOrOptions};
|
|
12
|
+
|
|
13
|
+
element[contextMetaKeyProvider] = new BlockquoteControllerContextMeta(element, ctx);
|
|
14
|
+
return element[contextMetaKeyProvider];
|
|
15
|
+
};
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
import {Directive, directive, PartType} from 'lit/directive.js';
|
|
2
|
+
import {noChange} from 'lit';
|
|
3
|
+
import {cacheContextMetaProvider, contextMetaKeyProvider} from './cache-context-meta-provider.js';
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* `contextMetaProviderDirective` is a Lit directive that allows you to make normal DOM elements context providers.
|
|
7
|
+
* This directive can be used in both attribute and element bindings in Lit templates.
|
|
8
|
+
*
|
|
9
|
+
* > https://github.com/lit/lit/discussions/4690
|
|
10
|
+
*
|
|
11
|
+
* Usage:
|
|
12
|
+
* This directive converts a DOM element into a Lit context provider using the BlockquoteControllerContextMeta class, which is a
|
|
13
|
+
* Lit Reactive Controller that encapsulates the controllers provided by [@lit/context](https://lit.dev/docs/data/context/).
|
|
14
|
+
*
|
|
15
|
+
* ## Features
|
|
16
|
+
* - Allows non-Lit elements to provide context.
|
|
17
|
+
* - Works seamlessly with [`@lit/context`](https://lit.dev/docs/data/context/).
|
|
18
|
+
* - Utilizes `BlockquoteControllerContextMeta`, a Lit Reactive Controller for managing context.
|
|
19
|
+
|
|
20
|
+
*
|
|
21
|
+
* js```
|
|
22
|
+
* <div ${contextMetaProviderDirective(myContext, someValue)}>
|
|
23
|
+
* <!-- Children can consume the provided context -->
|
|
24
|
+
* </div>
|
|
25
|
+
* //
|
|
26
|
+
* <div data-info="${contextMetaProviderDirective(myContext, someValue)}"">
|
|
27
|
+
* <!-- Children can consume the provided context -->
|
|
28
|
+
* </div>
|
|
29
|
+
* ```;
|
|
30
|
+
*/
|
|
31
|
+
class ContextMetaProviderDirective extends Directive {
|
|
32
|
+
/** @type {*} */
|
|
33
|
+
#partInfo = undefined;
|
|
34
|
+
#currentValue = undefined;
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* @param {import('lit/directive.js').PartInfo} partInfo - Information about the part this directive is bound to
|
|
38
|
+
*/
|
|
39
|
+
constructor(partInfo) {
|
|
40
|
+
super(partInfo);
|
|
41
|
+
if (partInfo.type !== PartType.ATTRIBUTE && partInfo.type !== PartType.ELEMENT) {
|
|
42
|
+
throw new Error(
|
|
43
|
+
'contextMetaProviderDirective can only be used in an attribute or element directive.'
|
|
44
|
+
);
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
this.#partInfo = partInfo;
|
|
48
|
+
}
|
|
49
|
+
|
|
50
|
+
/**
|
|
51
|
+
* Main render method called by Lit.
|
|
52
|
+
* @param {*} value - The context value to provide.
|
|
53
|
+
* @param {{
|
|
54
|
+
* context?: *,
|
|
55
|
+
* initialValue?: import('@lit/context').ContextType<*>,
|
|
56
|
+
* }} context - The context object.
|
|
57
|
+
* @returns {unknown} - The serialized context value or noChange.
|
|
58
|
+
*/
|
|
59
|
+
render(value, context) {
|
|
60
|
+
if (value !== this.#currentValue) {
|
|
61
|
+
this.#currentValue = value;
|
|
62
|
+
this.updateValue(value, context);
|
|
63
|
+
return this.resolveAttrValue();
|
|
64
|
+
}
|
|
65
|
+
return noChange;
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
/**
|
|
69
|
+
* Updates the context value for the element.
|
|
70
|
+
* @param {*} value - The new context value.
|
|
71
|
+
* @param {{
|
|
72
|
+
* context?: *,
|
|
73
|
+
* initialValue?: import('@lit/context').ContextType<*>,
|
|
74
|
+
* }} context - The context object.
|
|
75
|
+
*/
|
|
76
|
+
updateValue(value, context) {
|
|
77
|
+
const element = this.#partInfo.element;
|
|
78
|
+
cacheContextMetaProvider(element, context);
|
|
79
|
+
element[contextMetaKeyProvider].setValue(value);
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
/**
|
|
83
|
+
* Decides whether to return the currentValue if the directive is used as an attribute.
|
|
84
|
+
* @returns {unknown} - The serialized context value or noChange.
|
|
85
|
+
*/
|
|
86
|
+
resolveAttrValue() {
|
|
87
|
+
if (this.#partInfo.type !== PartType.ATTRIBUTE) {
|
|
88
|
+
return noChange;
|
|
89
|
+
}
|
|
90
|
+
return this.#currentValue;
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
|
|
94
|
+
export const contextMetaProvider = directive(ContextMetaProviderDirective);
|
package/src/index.js
CHANGED
|
@@ -1,2 +1,7 @@
|
|
|
1
1
|
export {BlockquoteControllerContextMeta} from './BlockquoteControllerContextMeta.js';
|
|
2
2
|
export {BaseContextMetaElement} from './BaseContextMetaElement.js';
|
|
3
|
+
export {contextMetaProvider} from './directives/context-meta-provider.js';
|
|
4
|
+
export {
|
|
5
|
+
cacheContextMetaProvider,
|
|
6
|
+
contextMetaKeyProvider,
|
|
7
|
+
} from './directives/cache-context-meta-provider.js';
|