我有一个 Aurelia 组件,它只是应该显示项目列表。组件的模型有一个可绑定的“items”属性:
@bindable items = [];
Run Code Online (Sandbox Code Playgroud)
组件模板使用简单的重复属性显示列表:
<div repeat.for="item of items">
${item.id} </div>
Run Code Online (Sandbox Code Playgroud)
当我从使用该组件的页面视图模型中将新项目推送到绑定数组中时,我可以看到在刷新列表并出现新项目时添加了该项目。我的问题是,当修改“items”数组时,我需要执行其他操作,因此我尝试将 collectionObserver 添加到组件中,如下所示:
import {BindingEngine, inject} from 'aurelia-framework';
@inject(BindingEngine)
export class GridControl {
@bindable items = [];
constructor(bindingEngine) {
this.items = [];
let subscription = bindingEngine.collectionObserver(this.items)
.subscribe(this.listChanged);
}
listChanged(splices) {
// do some stuff
}
}
Run Code Online (Sandbox Code Playgroud)
但是我的“listChanged”处理程序永远不会被调用。知道为什么吗?
我正在尝试创建一个自定义表格行,但很难让它正常运行。我尝试了以下两种方法,它们给出了奇怪的结果。我意识到这很容易在没有自定义元素的情况下实现,但这是一个更大项目的一个小例子。我可以改变什么来达到预期的结果?
class customTableRow extends HTMLElement {
constructor(){
super();
var shadow = this.attachShadow({mode: 'open'});
this.tableRow = document.createElement('tr');
var td = document.createElement('td');
td.innerText = "RowTitle";
this.tableRow.appendChild(td);
var td2 = document.createElement('td');
td2.innerText = "RowContent";
td2.colSpan = 4;
this.tableRow.appendChild(td2);
shadow.appendChild(this.tableRow);
}
}
customElements.define('custom-tr', customTableRow);
//Attempt 2
var newTr = new customTableRow;
document.getElementById('table2Body').appendChild(newTr);Run Code Online (Sandbox Code Playgroud)
td {
border: 1px solid black;
}Run Code Online (Sandbox Code Playgroud)
<span>Attempt 1:</span>
<table>
<thead>
<tr>
<th>One</th>
<th>Two</th>
<th>Three</th>
<th>Four</th>
<th>Five</th>
</tr>
</thead>
<tbody>
<custom-tr />
</tbody>
</table>
<hr>
<span>Attempt 2:</span>
<table id="table2">
<thead>
<tr>
<th>One</th> …Run Code Online (Sandbox Code Playgroud)我想从一个<select>元素制作一个 web 组件。我试图让<option>用户提供的标签出现在 Shadow DOM 中。
我的组件:
let tmpl = document.createElement('template');
tmpl.innerHTML = `
<select placeholder="text">
<slot name="option"></slot>
</select>
`;
class SelectBox extends HTMLElement {
constructor() {
super();
if (!this.shadowRoot) {
this.root = this.attachShadow({mode: 'open'});
this.root.appendChild(tmpl.content.cloneNode(true));
}
}
}
customElements.define('select-box', SelectBox);
Run Code Online (Sandbox Code Playgroud)
HTML:
<select-box>
<option slot="option" value="text">text</option>
</select-box>
Run Code Online (Sandbox Code Playgroud)
这让我相信我还没有掌握将用户元素插入 shadow DOM 的过程。
我需要找到一种非常高效的方法来确定自定义元素或其任何父元素是否具有 display: none;
第一种方法:
checkVisible() {
let parentNodes = [];
let el = this;
while (!!(el = el.parentNode)) {
parentNodes.push(el);
}
return [this, ...parentNodes].some(el => el.style.display === 'none')
}
Run Code Online (Sandbox Code Playgroud)
有什么比这运行得更快的吗?这甚至是一种安全的方法吗?
我需要这个的原因:我们有一个<data-table>自定义元素(原生 webcomponent),它在它的connectedCallback(). 我们有一个应用程序,在单个页面中包含 20-30 个自定义元素,这导致 IE 11 需要大约 15 秒才能呈现页面。
我需要延迟那些<data-table>最初甚至不可见的组件的初始化,所以我需要一种方法来测试connectedCallback()元素是否可见(如果它在最初未显示的 18 个选项卡之一中,则不是)。
javascript web-component custom-element native-web-component
我正在尝试将图像插入使用Stencil构建的Web组件中。
我遇到2个错误:
AppLogo is declared but its value is never read.
和
Cannot find module ../assets/logo.svg.
目录:
- src
-- components
--- app-header
---- assets
----- logo.svg
---- app-header.tsx
---- app-header.scss
---- app-header.spec.ts
Run Code Online (Sandbox Code Playgroud)
码:
import { Component } from "@stencil/core";
import AppLogo from "../assets/logo.svg";
@Component({
tag: "app-header",
styleUrl: "app-header.scss"
})
export class AppHeader {
render() {
return (
<header class="app-header">
<a href="#" class="app-logo">
<img src="{AppLogo}" alt="App Name" />
</a>
</header>
);
}
}
Run Code Online (Sandbox Code Playgroud)
(我可以找到)关于此的大量文档。因此,感谢您的帮助。
我有一个 Stencil.JS 组件:
import {Component, Prop, h} from '@stencil/core';
@Component({
tag: 'my-comp',
styleUrl: 'my-comp.css',
// shadow: true
})
export class MyComp {
@Prop() active: boolean = false;
render() {
return this.active ? <div>
<slot></slot>
</div> : null;
}
}
Run Code Online (Sandbox Code Playgroud)
当我以这种方式使用组件时,我希望插槽的内容不会呈现:
<my-comp>
<p>I'm hidden!</p>
</my-comp>
Run Code Online (Sandbox Code Playgroud)
而且,实际上它按预期工作,当“阴影”在组件装饰器中设置为 true 时。但是,当禁用 shadow DOM 时,无论 this.active 的值如何,组件都会显示 slot 的内容。
我有一种感觉,我不明白渲染是如何与插槽一起工作的。你能给我解释一下吗?如果您知道如何在不以编程方式隐藏插槽内容的情况下解决此问题,我将非常感激。
我正在尝试使用Polymer 项目中的PWA Starter Kit制作一个小应用程序。
是否可以在我的 LitElement 中使用来自https://material.io/develop/web/components/input-controls/text-field/的 Web 组件?我想使用文本区域。
我尝试过的:
import {html, customElement, LitElement} from "lit-element";
//
import {MDCTextField} from '@material/textfield';
@customElement('text-editor')
export class TextEditor extends LitElement {
protected render() {
return html`<div class="mdc-text-field mdc-text-field--textarea">
<textarea id="textarea" class="mdc-text-field__input" rows="8" cols="40"></textarea>
<div class="mdc-notched-outline">
<div class="mdc-notched-outline__leading"></div>
<div class="mdc-notched-outline__notch">
<label for="textarea" class="mdc-floating-label">Textarea Label</label>
</div>
<div class="mdc-notched-outline__trailing"></div>
</div>
</div>`
}
}
Run Code Online (Sandbox Code Playgroud)
但是,因为我不在任何地方使用“MDCTextField”,TypeScript 编译器抱怨“'MDCTextField' 已声明,但它的值从未被读取。”。
我确实在 HTML 中呈现了一个文本区域,但没有应用任何样式。
如何在 LitElement 中重用 MDCTextField Web 组件?
在处理光照元素组件库时,我遇到了一个尴尬的场景。
我目前正在处理的组件是“警报”。在它的渲染模板中,它有两个命名槽:“title”和“text”。
<div class="alert-item-content">
<i class="alert-item-icon"></i>
<slot name="title"></slot>
<slot name="text"></slot>
</div>
Run Code Online (Sandbox Code Playgroud)
分配给这些插槽的元素可能是任何有效的文本标签(h1、h2、h3 等)。我需要将插槽的分配元素定位到 A) 删除/重置影响它们的全局样式和 B) 添加对 UI 要求至关重要的特定样式。
因此,换句话说,一个人可能会提供一个“h5”,因为它在语义上是正确的,但作为一个警告标题,它应该始终显示相同。
例子:
<mult-alert>
<mult-alert-item>
<h5 slot="title">Notice Me</h5>
<p slot="text">
This is something you should probably
<a href="#">pay attention to</a>
</p>
</mult-alert-item>
</mult-alert>
Run Code Online (Sandbox Code Playgroud)
到目前为止,我能想到的唯一解决方案是查询 shadowRoot 中分配的元素并向它们添加一个类。它确实有效,但感觉很糟糕。这是来自组件的相关代码:
addClassesToSlottedNodes() {
[{
slotName: 'title',
className: 'alert-item-title'
}, {
slotName: 'text',
className: 'alert-item-text'
}].forEach(n => {
const slotNodes = this.shadowRoot
.querySelector(`slot[name="${n.slotName}"]`)
.assignedNodes();
if (slotNodes && slotNodes.length) {
slotNodes[0].classList.add(n.className);
}
})
}
Run Code Online (Sandbox Code Playgroud)
有没有更好的方法来定位这些带槽的元素而不用这种方式添加类?或者,是否有更简洁的方法在组件模板中添加类?
正如文档所说:
每次将自定义元素附加到文档连接元素时都会触发 connectedCallback
还:
firstUpdated 在您的组件第一次更新和呈现后触发
问题是我无法弄清楚它们之间的区别。那么区别是什么呢?当我应该使用connectedCallback,当firstUpdated生命周期挂钩?
使用 stenciljs 制作的 Web 组件不扩展 HTMLElement。我如何访问本机属性并在我的组件中使用它们,比如title属性?当我@Prop() title在模板中添加并使用它时,会显示错误。
添加@Prop()还会使属性在生成的文档中可见。如何将使用的或必需的本机属性添加到生成的文档中?
我得到的编译器错误:
The @Prop() name "title" is a reserved public name. Please rename the "title" prop so it does not conflict
with an existing standardized prototype member. Reusing prop names that are already defined on the element's
prototype may cause unexpected runtime errors or user-interface issues on various browsers, so it's best to
avoid them entirely.
Run Code Online (Sandbox Code Playgroud) web-component ×10
javascript ×5
html ×3
lit-element ×3
stenciljs ×3
typescript ×2
aurelia ×1
jsx ×1
polymer ×1
shadow-dom ×1