Web 组件只渲染一次

Web component only rendered once

*** 找出 1 个可行的解决方案,请在下面回答。***

这是我第一次使用 Web 组件。我创建了一个名为 article-component 的 Web 组件。当我将 article-component 添加到我的 HTML 时,它起作用了。当我添加另一个文章组件时,它没有完全呈现。内容未呈现,只是一个轮廓。有趣的是,在元素中,所有看不见的阴影根都是空的。

我的代码,

index.html

<!doctype html>

<html lang="en">

<head>
  <meta charset="utf-8">
  <meta name="viewport" content="width=device-width, initial-scale=1">

  <title>title</title>

  <link rel="stylesheet" href="css/style.css">
  <script src="js/components/article.js"></script>

</head>

<body>
  <div id="screen">
    <div class="page">
      <div class="title">
        <h1>yesterday</h1>
      </div>
      <div class="body">
        <article-component></article-component>
        <article-component></article-component>
        <article-component></article-component>
        <article-component></article-component>
      </div>
    </div>
  </div>
  <script src="js/script.js"></script>
</body>

</html>

style.css

/* Reset CSS for browser consistency */
html,
body,
h1,
h3,
h4,
p {
  width: 100%;
  height: 100%;
  margin: 0;
  padding: 0;
  border: 0;
  font-size: 20px;
  font-weight: 400;
}

/* Screen */
#screen {
  width: 100%;
  height: 100%;
  display: flex;
  flex-direction: column;
  background-color: #ffffff;
}

/* Page */
.page {
  width: 100%;
  display: flex;
  flex-direction: column;
  align-items: center;
}

.title {
  width: 100%;
  text-align: center;
  padding: 8px;
  margin: 8px;
}

.body {
  width: 100%;
  display: flex;
  flex-direction: row;
  flex-wrap: wrap;
  justify-content: center;
}

/* Article */
article-component {
  width: 33%;
}

@media screen and (orientation: portrait) {
  article-component {
    width: 80%;
  }
}

/* Text */
h1 {
  font-size: 2rem;
  font-weight: normal;
}

h3 {
  font-size: 1.2rem;
  font-weight: lighter;
  line-height: 1.8rem;
}

h4 {
  width: auto;
  font-size: 1rem;
  font-weight: 500;
}

p {
  letter-spacing: 1px;
  line-height: 1.5rem;
}

article.js

const articleTemplate = document.createElement("template");
articleTemplate.innerHTML = `

<link rel="stylesheet" href="css/style.css">
<link rel="stylesheet" href="css/components/article.css">

<div class="article">
    <div class="heading">
        <h3>Indian Migrant Labourers Covid19 Crisis</h3>
    </div>
    <div class="content">
        <p>
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Vestibulum gravida efficitur mi vel malesuada.
            Nunc id nulla odio. Ut convallis tristique vehicula. Suspendisse potenti. Mauris tempor, ligula ut tincidunt
            venenatis, ex enim placerat arcu, nec venenatis urna sem varius libero. Quisque quis augue eu neque euismod
            luctus. Integer mauris neque, vulputate sit amet velit quis, hendrerit aliquam risus. Vivamus ultrices neque
            lorem, nec laoreet elit viverra non.
        </p>
    </div>
    <div class="sources">
        <div class="source">
            <h4>[1]&nbsp</h4>
            <h4>Lorem ipsum dolor sit amet.</h4>
        </div>
    </div>
</div>
`;

class Article extends HTMLElement {
  constructor() {
    super();
  }

  connectedCallback() {
    const shadowRoot = this.attachShadow({ mode: "open" });
    shadowRoot.appendChild(articleTemplate.content);
  }
}

customElements.define("article-component", Article);

article.css

.article {
  width: 100%;
  display: flex;
  flex-direction: column;
  align-items: center;
  padding: 8px;
}

.heading {
  padding: 8px;
}

.content {
  padding: 4px;
}

.sources {
  width: 100%;
  display: flex;
  flex-direction: column;
  margin-left: 8px;
  margin-top: 8px;
}

/* Source */
.source {
  width: 100%;
  display: flex;
  flex-direction: row;
  justify-content: flex-start;
}

在 article.js 中编辑以下行 -> connectedCallback() 有效:

shadowRoot.appendChild(articleTemplate.content);

shadowRoot.appendChild(articleTemplate.content.cloneNode(true));

我不知道为什么。

注:

 constructor() {
    super();
  }

  connectedCallback() {
    const shadowRoot = this.attachShadow({ mode: "open" });
    shadowRoot.appendChild(articleTemplate.content);
  }

可以(更好)写成:

 constructor() {
    super() // set and returns 'this'
       .attachShadow({ mode: "open" })  // sets and returns this.shadowRoot
       .append(articleTemplate.content); // see MDN documentation why append is better
  }

因为connectedCallback可以触发多次;例如。当您移动 DOM 个节点时。