函数 addEventListener 不适用于 Fetch

Function addEventListener doesn't work with Fetch

我在做什么:
我正在为我制作一个作品集,使用 HTML、CSS 和 JavaScript pure。我正在创建项目页面并尝试使用 JavaScript 创建 <p> 并从 .json 文件插入数据,但是:

有什么问题吗?
Fetch API 不适用于 addEventListener。

我试过:
先创建<p>,然后从addEventListener函数中插入数据,也不起作用。

部分JavaScript:

async setProjects(){
  let response = await fetch("contents/projects.json");
  let responseJson = await response.json();
    
  document.addEventListener("DOMContentLoaded", function () {
    var p = document.createElement('p');
    
    p.innerHTML = responseJson.one.bio;
    p.id = "bio-project";
    // p.style.cssText = 'border-left: 8px solid aqua;';
    
    document.querySelector(".projeto-contents").appendChild(p);
  }, false)
}

HTML:

<!DOCTYPE html>
<html lang="pt-br">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Projetos - Vitor Hugo's Portifolio</title>
    <link rel="stylesheet" href="../style.css" />
    <script type="text/javascript" src="script.js"></script>
  </head>

  <body>
    <header>
      <nav>
        <a class="logo" href="/">Vitor Hugo</a>
        <div class="mobile-menu">
          <div class="line-1"></div>
          <div class="line-2"></div>
          <div class="line-3"></div>
        </div>
        <ul class="nav-list">
          <li><a href="index.html">Home</a></li>
          <li><a href="sobre.html">Sobre</a></li>
          <li><a href="projetos.html">Projetos</a></li>
          <li><a href="contatos.html">Contato</a></li>
        </ul>
      </nav>
    </header>
    <script src="../mobile-screen.js"></script>

    <!--  -->
    <div class="projetos">
      <div class="projeto-contents">
        <h1 id="titulo-project">test</h1>
      </div>
    </div>
    <script language="javascript">
      const portifolio = new Portifolio();
      portifolio.setProjects();
    </script>
  </body>
</html>

JSON:

{
  "one":{
    "name":"Lorem",
    "bio":"Lorem ipsum dolor sit amet consectetur adipisicing elit. Eos dolore pariatur accusamus quaerat hic distinctio, cum, ratione dignissimos, doloremque incidunt provident deleniti consectetur qui alias quam quod porro error temporibus.",
    "language":"Python"
  },
  "two":{
    "name":"testname2",
    "bio":"testbio2",
    "language":"testlanguage2"
  },
  "three":{
    "name":"testname3",
    "bio":"testbio3",
    "language":"testlanguage3"
  },
  "four":{
    "name":"testname4",
    "bio":"testbio4",
    "language":"testlanguage4"
  }
}

项目 link:https://github.com/vitorhugo1207/portfolio

我必须做什么?请帮我。还有一件事:关于 json 可以使用数字作为索引吗?抱歉,我正在学习英语,如有拼写和语法错误。

async/await 允许您编写看起来像是同步的代码,但实际上并非如此——它只是处理 promises 的语法糖。

fetch()发送AJAX请求后,浏览器继续加载文档。当它完成时,DOM 已经加载并且 DOMContentLoaded 事件已经触发,所以为它添加事件侦听器为时已晚。

您可以从 fetch() 获得承诺并在 DOMContentLoaded 侦听器中使用其 .then() 方法。

setProjects() {
  let response_promise = fetch("contents/projects.json");

  document.addEventListener("DOMContentLoaded", function() {
    response_promise.then(response => response.json().then(responseJson => {
      var p = document.createElement('p');

      p.innerHTML = responseJson.one.bio;
      p.id = "bio-project";
      // p.style.cssText = 'border-left: 8px solid aqua;';

      document.querySelector(".projeto-contents").appendChild(p);
    }))
  }, false)
}

document.addEventListener("DOMContentLoaded", async () => {
  const response = await fetch("contents/projects.json").then((res) => res.json());
  const paragraph = document.createElement("p");
  paragraph.innerHTML = response.one.bio;
  paragraph.id = "bio-project";
  // p.style.cssText = 'border-left: 8px solid aqua;';

  document.querySelector(".projeto-contents").appendChild(paragraph);
});
<!DOCTYPE html>
<html lang="pt-br">
  <head>
    <meta charset="UTF-8" />
    <meta http-equiv="X-UA-Compatible" content="IE=edge" />
    <meta name="viewport" content="width=device-width, initial-scale=1.0" />
    <title>Projetos - Vitor Hugo's Portifolio</title>
    <link rel="stylesheet" href="../style.css" />
    <script defer src="./index.js"></script>
  </head>

  <body>
    <header>
      <nav>
        <a class="logo" href="/">Vitor Hugo</a>
        <div class="mobile-menu">
          <div class="line-1"></div>
          <div class="line-2"></div>
          <div class="line-3"></div>
        </div>
        <ul class="nav-list">
          <li><a href="index.html">Home</a></li>
          <li><a href="sobre.html">Sobre</a></li>
          <li><a href="projetos.html">Projetos</a></li>
          <li><a href="contatos.html">Contato</a></li>
        </ul>
      </nav>
    </header>

    <div class="projetos">
      <div class="projeto-contents">
        <h1 id="titulo-project">test</h1>
      </div>
    </div>
  </body>
</html>

您在 DOM 已经呈现到您的页面后触发 DOMContentLoaded。 同样在您的 HTML 中,您使用的是不带 defer 属性的内容。 基本上 defer 是告诉浏览器在解析文档后执行 script 或者你可以将它附加到正文 <script src="./index.js"></script> .

我也在使用 Promise API,如果您想了解更多信息,请查看 PromiseAPI or about async/await