VUE之旅—day2

文章目录

  • Vue生命周期和生命周期的四个阶段
        • created应用—新闻列表渲染
        • mounted应用—进入页面搜索框就获得焦点
        • 账单统计(Echarts可视化图表渲染)

Vue生命周期和生命周期的四个阶段

思考:

什么时候可以发送初始化渲染请求?(越早越好)

什么时候可以开始操作dom?(至少dom得渲染出来)

Vue生命周期: 一个Vue实例从创建到销毁的整个过程

生命周期四个阶段: ①创建②挂载③更新④销毁

VUE之旅—day2_第1张图片

VUE之旅—day2_第2张图片

Vue生命周期函数(钩子函数)

Vue生命周期过程中,会自动运行一些函数,被称为【生命周期钩子】—>让开发者可以在【特定阶段】运行自己的代码。

VUE之旅—day2_第3张图片

代码说明

<!DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>生命周期的四个阶段</title>
</head>

<body>
  <div id="app">
    <h1>{{title}}</h1>
    <button @click="sub">-</button>
    <span>{{count}}</span>
    <button @click="add">+</button>
  </div>
  <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.js"></script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        count: 100,
        title: '计数器'
      },
      // 1.创建阶段(准备数据)
      beforeCreate() {
        console.log('beforeCreate 响应式数据准备好之前', this.count);//undefined
      },
      created() {
        // created,这一阶段开始,就能发送初始化渲染请求
        console.log('Created 响应式数据准备好之后', this.count);// 100
      },

      // 2.挂载阶段(渲染模板)
      beforeMount() {
        console.log('beforeMount 模板渲染之前', document.querySelector('h1').innerHTML);// {{title}}
      },
      mounted() {
        // created,这一阶段开始,就能操作dom了
        console.log('mounted 模板渲染之后', document.querySelector('h1').innerHTML);// 计数器
      },

      // 3.更新阶段(修改数据 → 更新视图)
      beforeUpdate() {
        console.log('beforeUpdate 数据修改了,视图还没更新', document.querySelector('span').innerHTML);
      },
      updated() {
        console.log('Updated 数据修改了,视图已经更新', document.querySelector('span').innerHTML);
      },
      //4.卸载阶段
      //Vue提供了一个语法 Vue对象名.$destroy()  用来查看卸载状态
      beforeDestroy() {
        console.log('beforeDestory 卸载前');
        console.log('清除掉一些Vue以外的资源占用,定时器,延时器...');
      },
      destroyed() {
        console.log('destroyed 卸载后');
      },
      methods: {
        add() {
          this.count++
        },
        sub() {
          this.count--
        }
      }
    })
  </script>
</body>

</html>
created应用—新闻列表渲染




  
  
  新闻列表渲染
  



  
  • {{item.title}}
    {{item.source}} {{item.time}}
mounted应用—进入页面搜索框就获得焦点
DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>搜索框一进入就获得焦点title>
  <style>
    .container {
      width: 600px;
      height: auto;
      margin: 0 auto;
    }

    .container .seacher-container {
      width: 100%;
      height: 150px;
      text-align: center;
      background-color: aliceblue;
    }

    .container .seacher-container .search-box {
      width: 80%;
      height: 35px;
      margin: 20px auto;
      border: 1px solid #8b8b8b;
      display: flex;
      border-radius: 5px;
      justify-content: flex-end;
      align-items: center;
      background-color: #ffffff;
      border-right: none;
    }

    .container .seacher-container .search-box input {
      width: 78%;
      height: 90%;
      border: none;
      outline: none;
      background-color: #ffffff;

    }

    .container .seacher-container .search-box button {
      width: 20%;
      height: 106%;
      border: none;
      outline: none;
      background-color: #ea2704;
      color: #f5f5f5;
      border-radius: 5px;
      border-top-left-radius: 0;
      border-bottom-left-radius: 0;
      cursor: pointer;
    }
  style>
head>

<body>
  <div class="container" id="app">
    <div class="seacher-container">
      <img src="http://www.itheima.com/images/logo.png" alt="">
      <div class="search-box">
        <input type="text" v-model="words" id="inp" autocomplete="off">
        <button>搜索一下button>
      div>
    div>
  div>
  <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.js">script>
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        words: ''
      },
      // 核心思路:
      // 1.等输入框渲染出来
      // 2.让输入框获取焦点
      mounted() {
        document.querySelector('#inp').focus()
      }
    })
  script>
body>

html>
账单统计(Echarts可视化图表渲染)
DOCTYPE html>
<html lang="en">

<head>
  <meta charset="UTF-8">
  <meta name="viewport" content="width=device-width, initial-scale=1.0">
  <title>Documenttitle>
  <style>
    #app {
      margin: 0 auto;
      width: 1100px;
      height: auto;
    }

    h3 {
      color: #8d5252;
    }

    /* https://www.apifox.cn/apidoc/shared-24459455-ebb1-4fdc- */
    .container {
      width: 1100px;
      display: flex;
      justify-content: space-between;
    }

    .container #tableArea {
      width: 50%;
      height: auto;
    }

    .container #tableArea .iptArea {
      width: 100%;
      height: 30px;
      margin-bottom: 10px;
    }

    .container #tableArea .iptArea input {
      width: 40%;
      height: 100%;
      border: 1px solid #e2e1e1;
      border-radius: 4px;
      text-indent: 5px;
      outline: none;
    }

    .container #tableArea .iptArea button {
      width: 15%;
      height: 110%;
      border: none;
      outline: none;
      background-color: rgb(9, 114, 206);
      color: #fff;
      border-radius: 4px;
      cursor: pointer;
    }

    .container #tableArea table {
      width: 100%;
      height: auto;
      text-align: left;
      border-collapse: collapse;
      font-size: 14px;
    }

    .container #tableArea table tr {
      height: 40px;
      border-bottom: 1px solid #eee;
    }

    .container #tableArea table tr .red {
      color: red;
    }

    .container #tableArea table tr td a {
      color: rgb(42, 97, 238);
      text-decoration: none;
    }

    .container #chartArea {
      width: 45%;
      height: 330px;
      border: 1px solid #eee;
      padding: 10px;
    }

    @media (max-width: 768px) {
      .container {
        width: 600px;
        flex-wrap: wrap;
        justify-content: center;
      }

      .container #tableArea {
        width: 90%;
      }

      .container #chartArea {
        width: 90%;
      }
    }

    @media (min-width: 1200px) {
      .container {
        width: 1100px;
        flex-wrap: wrap;
      }

      .container #tableArea {
        width: 50%;
      }

      .container #chartArea {
        width: 45%;
      }
    }
  style>
head>

<body>
  <div id="app">
    <h3>小黑记账清单h3>
    <div class="container">
      <div id="tableArea">
        <div class="iptArea">
          <input type="text" placeholder="消费名称" v-model.trim="name">
          <input type="text" placeholder="消费价格" v-model.number="price">
          <button @click="addData">添加账单button>
        div>
        <table>
          <thead>
            <tr>
              <th>编号th>
              <th>消费名称th>
              <th>消费价格th>
              <th>操作th>
            tr>
          thead>
          <tbody>
            <tr v-for="(item,index) in list" :key="item.id">
              <td>{{index+1}}td>
              <td>{{item.name}}td>
              <td :class="{red:item.price>500}">{{item.price}}td>
              <td><a @click="delData(item.id)" href="javascript:;">删除a>td>
            tr>
          tbody>
          <tfoot>
            <tr>
              <th colspan="4">消费总计:<span>{{totalPrice}}span>th>
            tr>
          tfoot>
        table>
      div>
      <div id="chartArea">
        <div id="main" style="width:550px;height:330px;">div>
      div>
    div>
  div>
  <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/echarts.min.js">script>
  <script src="https://cdn.jsdelivr.net/npm/axios/dist/axios.min.js">script>
  <script src="https://cdn.jsdelivr.net/npm/[email protected]/dist/vue.js">script>
  
  <script>
    const app = new Vue({
      el: '#app',
      data: {
        list: [],
        name: '',
        price: ''
      },
      computed: {
        totalPrice() {
          return this.list.reduce((sum, item) => sum + item.price, 0).toFixed(2)
        }
      },
      created() {
        this.getData()
      },
      mounted() {
        this.myChart = echarts.init(document.getElementById('main'));
        this.myChart.setOption({
          title: {
            text: '消费账单列表',
            left: 'center'
          },
          tooltip: {
            trigger: 'item'
          },
          legend: {
            orient: 'vertical',
            left: 'left'
          },
          series: [
            {
              name: '消费账单',
              type: 'pie',
              radius: '50%',
              data: [

              ],
              emphasis: {
                itemStyle: {
                  shadowBlur: 10,
                  shadowOffsetX: 0,
                  shadowColor: 'rgba(0, 0, 0, 0.5)'
                }
              }
            }
          ]
        });

      },
      methods: {
        async getData() {
          const res = await axios.get('https://applet-base-api-t.itheima.net/bill', {
            params: {
              creator: '小黑'
            }
          })
          this.list = res.data.data
          this.myChart.setOption(
            {
              series: [
                {
                  data: this.list.map(item => ({ value: item.price, name: item.name }))
                }
              ]
            }
          )
        },
        async addData() {
          // 优化
          if (!this.name) {
            alert("请输入消费名称")
            return
          }
          if (typeof this.price !== 'number') {
            alert("请输入正确的消费价格")
            return
          }
          //发送添加请求
          const res = await axios.post('https://applet-base-api-t.itheima.net/bill', {
            creator: '小黑',
            name: this.name,
            price: this.price
          })
          console.log(res);
          // 重新再渲染一次
          this.getData()
          // 清空输入框
          this.name = ''
          this.price = ''
        },
        async delData(id) {
          const res = await axios.delete(`https://applet-base-api-t.itheima.net/bill/${id}`)
          console.log(res);
          // 重新再渲染一次
          this.getData()
        }
      }

    })
  script>
body>

html>

你可能感兴趣的:(前端,vue.js,javascript,前端)