Vue项目实战——实现GitHub搜索案例(学以致用,两小时带你巩固和强化Vue知识点)

Vue2.x 项目实战(二)

内容参考链接
Vue2.x全家桶Vue2.x 全家桶参考链接
Vue2.x项目(一)Vue2.x 实现一个任务清单
Vue2.x项目(二)Vue2.x 实现GitHub搜索案例
Vue3.x项目(三)Vue3.x 实现一个任务清单


Vue2.x 实现 github 搜索案例

1、前言

如果你对 vue 的基础知识还很陌生,推荐先去学习一下 vue 基础

本篇文章依旧是使用的 Vue 基础知识,同时新增了 axios 请求数据 的需求,及 兄弟组件间 如何 使用自定义事件 实现组件间通信

  • 如果你 刚学完 vue 基础知识,想检查一下自己的学习成果
  • 如果你 已学完 vue 基础知识,想快速回顾复习
  • 如果你 已精通 vue 基础知识,想做个小案例
  • 那不妨 再看完这篇文章我保证你一定会更有收获的!

2、项目演示(一睹为快)

github 搜索案例

在这里插入图片描述

3、涉及知识点

  • Vue基础:插值语法,常用指令,列表渲染,生命周期
  • Vue进阶:自定义事件(兄弟组件间通信),自定义事件的解绑
  • 第三方库:axios(发送 axios 请求,请求数据),vue-lazyload 插件,实现 图片懒加载

备注:

  1. 任意组件间的通信方式有很多种(全局事件总线,消息订阅预发布…),熟练掌握一种即可
  2. 本文是 vue 基础的练习项目,不涉及 vue 周边(Vuex,Vue-router)

4、项目详情(附源码及解析)

该项目包含三个 vue 组件

(1)App.vue 父组件:整合子组件

(2)Search.vue 子组件:用户查询,发送请求,获取数据

(3)List.vue 子组件:展示用户图片和信息的列表

备注:

  1. github 提供的请求 API:https://api.github.com/search/users?q=xxx
  2. 请求的数据(用到的红框起来了)
    在这里插入图片描述

App.vue 父组件

<template>
  <div class="container">
    <Search />
    <List />
  </div>
</template>

<script>
import Search from "./components/Search.vue";
import List from "./components/List.vue";
export default {
  name: "App",
  components: { Search, List },
};
</script>

Search.vue 子组件

  • 终端键入 npm i axios 安装 axios
  • 给按钮添加点击事件,axios 请求数据并进行页面的渲染更新
  • 兄弟组件间通过自定义事件通信,要引入一个 event.js 文件,暴露一个 vue 实例
<template>
  <section class="jumbotron">
    <h3 class="jumbotron-heading">Search Github Users</h3>
    <input
      type="text"
      placeholder="enter the name you search"
      v-model="keyWords"
    />&nbsp;
    <button @click="searchUsers">Search</button>
  </section>
</template>

<script>
import axios from "axios";
import event from '../event'
export default {
  name: "mySearch",
  data() {
    return {
      keyWords: "", // 用户输入的关键字
    };
  },
  methods: {
    // 查询用户
    searchUsers() {
      // 请求前更新 List 的数据
      event.$emit("updateListData", {
        isFirst: false, // 隐藏欢迎词
        isLoading: true, // 展示加载中...
        errMsg: "", // 错误信息为空
        users: [], // 数据置为空
      });
      axios.get(`https://api.github.com/search/users?q=${this.keyWords}`).then(
        // 成功的回调,隐藏欢迎和加载中,展示请求出来的数据
        (reponse) => {
          console.log("请求成功了", reponse.data.items);
          // 请求成功后更新 List 数据
          event.$emit("updateListData", {
            isLoading: false, // 请求成功,隐藏加载中...
            errMsg: "",
            users: reponse.data.items, // users 数组存放请求成功的数据
          });
        },
		// 失败的回调,提示错误信息
        (error) => {
          //请求失败后更新List数据
          console.log("请求失败了", error.message);
          event.$emit("updateListData", {
            isLoading: false, // 请求成功,隐藏加载中...
            errMsg: error.message, // 请求出错,展示错误信息
            users: [], // users 数组置空
          });
        }
      );
    },
  },
};
</script>

<style>
.jumbotron {
  margin-top: 20px;
}
.jumbotron-heading {
  color: skyblue;
}
</style>

List.vue 子组件

  • 终端键入 npm i vue-lazyload 安装懒加载插件
  • 在 main.js 中导入并使用它,并设置懒加载时的图片
  • 兄弟组件间通过自定义事件通信,要引入一个 event.js 文件,暴露一个 vue 实例
<template>
  <div class="row">
    <!-- 展示用户列表,没有内容时隐藏它。user.login,是唯一标识 -->
    <div
      v-show="info.users.length"
      class="card"
      v-for="user in info.users"
      :key="user.login"
    >
      <!-- 动态绑定用户的主页地址和图片地址 -->
      <a :href="user.html_url" target="_blank">
      	<!-- v-lazy 实现图片的懒加载 -->
        <img v-lazy="user.avatar_url" style="width: 100px; height: 100px" />
      </a>
      <!-- 呈现用户名 -->
      <p class="card-text">{{ user.login }}</p>
    </div>
    <!-- 初始页面,展示欢迎词 -->
    <h2 class="welcome" v-show="info.isFirst">前端杂货铺,欢迎你的使用!</h2>
    <!-- 点击查询,加载过程中展示加载中 -->
    <h2 class="loading" v-show="info.isLoading">加载中...</h2>
    <!-- 请求出错,展示错误信息 -->
    <h2 class="error" v-show="info.errMsg">{{ info.errMsg }}</h2>
  </div>
</template>

<script>
import event from "../event";
export default {
  name: "myList",
  data() {
    return {
      info: {
        isFirst: true, // 欢迎词
        isLoading: false, // 加载中...
        errMsg: "", // 错误信息
        users: [], // 存放用户的数组
      },
    };
  },
  // 挂载时绑定自定义事件
  mounted() {
    event.$on("updateListData", (dataObj) => {
      // 合并这两个对象,并且同 key 值的后面的会覆盖前面的,这样 isFirst 就不用重复写了
      this.info = { ...this.info, ...dataObj };
    });
  },
  // 销毁前解绑自定义事件
  beforeDestroy() {
    event.$off("updateListData");
  },
};
</script>

<style scoped>
.welcome {
  color: orange;
}
.loading {
  color: rgb(0, 162, 255);
}
.error {
  color: red;
}
.album {
  min-height: 50rem;
  padding-top: 3rem;
  padding-bottom: 3rem;
  background-color: #f7f7f7;
}

.card {
  float: left;
  width: 33.333%;
  padding: 0.75rem;
  margin-bottom: 2rem;
  border: 1px solid #efefef;
  text-align: center;
}

.card > img {
  margin-bottom: 0.75rem;
  border-radius: 100px;
}

.card-text {
  font-size: 85%;
}
</style>

main.js 文件

import Vue from 'vue'
import App from './App.vue'
import VueLazyload from 'vue-lazyload'

// 使用懒加载,并设置加载时的图片
Vue.use(VueLazyload, {
    loading: require("./assets/loading3.png")
})

new Vue({
    el:'#app',
    render: h => h(App),
})

event.js 文件

  • 暴露一个 vue 实例,供自定义事件进行兄弟组件间的通信
import Vue from 'vue'

export default new Vue()

5、写在最后的话

如果你是 看完全篇 阅读到了这里,我相信你一定是有收获的!

那么下面不妨打开自己的电脑,启动自己的编译器,来跟着做 / 自己做一遍吧!


在这里插入图片描述


  • 75
    点赞
  • 96
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 112
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 112
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

前端杂货铺

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值