坑: await 把 Promise 解析为普通对象,async 函数 return 的返回值是 promise 对象,await 后转化为普通 Object

需求: 需要在请求后端数据后,渲染时,边动态设置uni-icon的type类型

根据需求可知,需要使用同步请求,只能等设置完type才能进行渲染,如果异步请求,后台响应太慢了,此时Dom渲染完毕,就无法调用函数动态获取type了

或者等后台请求完,在给每个数据添加iconType,在刷新下数据,v-for进行呈现即可,这里使用的是第二种

<template>
 
  <view>
 
    <!-- 书籍浏览 -->
 
    <view class="box" v-for="(item, index) in books" :key="index">
 
      <view class="books">
 
        <image
 
          class="img"
 
          :src="item.picUrl"
 
          mode="widthFix"
 
          style="width: 150rpx"
 
        ></image>
 
        <view class="content" @click="bookDetailClick({ item })">
 
          <view class="tit">{{ item.bookName }}</view>
 
          <!-- <text class="num">{{ index + 1 }}</text> -->
 
          <view class="info">
 
            <!-- <view class="desc">{{ item.bookDesc }}</view> -->
 
            <u-parse class="desc" :content="item.bookDesc" />
 
            <view class="author">{{ item.authorName }}</view>
 
            <view class="category">{{ item.catName }}</view>
 
          </view>
 
        </view>
 
        <uni-icons
 
          class="icons"
 
          :type="item.iconType"
 
          size="20"
 
          @click="detail(item)"
 
        ></uni-icons>
 
      </view>
 
      <!-- 分割线 -->
 
      <view class="fengequyu"></view>
 
    </view>
 
  </view>
 
</template>
 
 
 
<script>
 
import { getBookList, getBookBySearch } from "@/common/api/book.js";
 
import {
 
  getQueryIsInShelf,
 
  addToBookShelf,
 
  removeFromBookShelf,
 
} from "@/common/api/bookshelf.js";
 
 
 
import { getBookDetailById } from "@/common/api/book.js";
 
 
 
export default {
 
  components: {},
 
  data() {
 
    return {
 
      iconType: "",
 
      keyword: "", //关键词
 
      workDirection: "", // 男频还是女频
 
      bookNameList: [],
 
      books: [],
 
      pageNum: 1,
 
      pageSize: 10,
 
      total: 0,
 
      flag: false, //用于显示数据见底输出提示信息
 
    };
 
  },
 
 
 
  created() {
 
    this.bookInit();
 
  },
 
 
 
  onLoad: function (options) {
 
    if (options.data) {
 
      var data = JSON.parse(decodeURIComponent(options.data));
 
      // 使用传递的数据
 
      console.log("传递search数据:", data);
 
      this.workDirection = data.workDirection;
 
      this.keyword = data.searchValue;
 
    }
 
    this.getBookBySearch();
 
  },
 
 
 
  onPullDownRefresh() {
 
    console.log("触发下拉刷新");
 
  },
 
  onReachBottom() {
 
    console.log("数据触底了");
 
    this.pageNum++;
 
 
 
    console.log(this.pageNum, "当前页码");
 
 
 
    if (this.pageNum > this.total / this.pageSize) {
 
      //数据已经拉取完,没有了
 
      flag = true;
 
      console.log("数据已经拉取完,没有了,显示提示信息");
 
    }
 
  },
 
 
 
  methods: {
 
    async bookInit() {
 
      this.books = [];
 
 
 
      //重新封装books,添加iconType
 
 
 
      // 在这里获取书籍列表,可能是从 API 获取
 
      const bookDatas = await this.getBookBySearch();
 
      // 为每本书设置图标类型
 
      for (const book of bookDatas.data.list) {
 
        book.iconType = await this.getType(book);
 
      }
 
      console.log("打印是否存在iconType", bookDatas.data.list);
 
 
 
      this.books = bookDatas.data.list; // 更新书籍列表数据
 
 
 
      console.log(this.books, "更新后books");
 
    },
 
 
 
    async detail(item) {
 
      console.log(item, "点击传输item");
 
 
 
      if (item.iconType == "plus") {
 
        let res = await getBookDetailById(item.id);
 
        const firstBookIndexId = res.data.firstBookIndexId;
 
        //加入书架
 
        await addToBookShelf(item.id, firstBookIndexId)
 
          .then((resAddToShelf) => {
 
            if (resAddToShelf.ok) {
 
              uni.showToast({
 
                title: "加入书架成功",
 
                icon: "none",
 
                mask: true,
 
                duration: 1000,
 
              });
 
              this.getType(item);
 
            } else {
 
              this.message("error", resAddToShelf.msg);
 
            }
 
          })
 
          .catch((error) => {
 
            this.message("error", "加入书架失败" + error);
 
          });
 
      } else {
 
        //移除书架
 
        removeFromBookShelf(item.id)
 
          .then((resRemoveToShelf) => {
 
            if (resRemoveToShelf.ok) {
 
              uni.showToast({
 
                title: "移出书架成功",
 
                icon: "none",
 
                mask: true,
 
                duration: 1000,
 
              });
 
              this.getType(item);
 
            } else {
 
              this.message("error", resRemoveToShelf.msg);
 
            }
 
          })
 
          .catch((error) => {
 
            this.message("error", "移出书架失败" + error);
 
          });
 
      }
 
    },
 
 
 
    async getType(item) {
 
      const resIsInShelf = await getQueryIsInShelf(item.id); //注意注意!!!这返回的是promise对象
 
      if (!resIsInShelf.data) {
 
        return "plus";
 
      } else {
 
        console.log("true");
 
        return "minus";
 
      }
 
    },
 
 
 
    message(type, message) {
 
      uni.showToast({
 
        title: message,
 
        icon: type,
 
        mask: true,
 
      });
 
    },
 
 
 
    //根据搜索结果获取书籍列表
 
    async getBookBySearch() {
 
      let res = await getBookBySearch(
 
        this.pageNum,
 
        this.pageSize,
 
        this.keyword,
 
        this.workDirection
 
      );
 
      console.log(res, "根据搜索结果获取书籍列表");
 
      this.books = [...this.books, ...res.data.list];
 
      this.total = res.data.total;
 
      return res;
 
    },
 
 
 
    //点击查看小说详情 公共函数,所有循环的对象都必须定义成item
 
    bookDetailClick(book) {
 
      console.log(book, "当前点击的数据");
 
      console.log(book.item.id, "当前点击的数据的id");
 
      uni.navigateTo({
 
        url: "/pages/bookdetail/bookdetail?bookId=" + book.item.id,
 
      });
 
    },
 
  },
 
};
 
</script>
 
 
 
<style lang="scss">
 
.uni-searchbar {
 
  /* #ifndef APP-NVUE */
 
  display: flex;
 
  /* #endif */
 
  flex-direction: row;
 
  position: relative;
 
  padding: 16rpx;
 
  /* 将默认的 #FFFFFF 改为 #C00000 */
 
  background-color: #c00000;
 
}
 
 
 
.icons {
 
  float: left;
 
  position: absolute;
 
  top: 50%;
 
  right: 10px;
 
  -webkit-transform: translateY(-50%);
 
  transform: translateY(-50%);
 
}
 
 
 
.fengequyu {
 
  width: 100%;
 
  height: 1rpx;
 
  background-color: #e8e8e8;
 
  //   margin-top: 100rpx;
 
}
 
 
 
::v-deep ._root {
 
  /* 超出部分隐藏 */
 
  display: -webkit-box;
 
  -webkit-line-clamp: 2;
 
  overflow: hidden;
 
  text-overflow: ellipsis;
 
  /* autoprefixer: off */
 
  -webkit-box-orient: vertical;
 
  /* autoprefixer: on */
 
}
 
 
 
.search-box {
 
  position: sticky;
 
  top: 0;
 
  z-index: 999;
 
}
 
 
 
.books {
 
  width: 100%;
 
  height: 240rpx;
 
 
 
  //定位垂直居中 子绝父相
 
  position: relative;
 
}
 
 
 
.img {
 
  float: left;
 
  margin-top: 10px;
 
}
 
 
 
.content {
 
  width: 480rpx;
 
  float: left;
 
  //间距
 
  margin-left: 22rpx;
 
  margin-top: 5rpx;
 
  text-align: left;
 
}
 
 
 
.tit {
 
  display: inline-block;
 
  font-size: 30rpx;
 
}
 
 
 
.num {
 
  float: right;
 
  color: red;
 
}
 
 
 
.info {
 
  margin-top: 10rpx;
 
}
 
 
 
.desc {
 
  font-size: 26rpx;
 
  color: #777777;
 
  /* 超出部分隐藏 */
 
  display: -webkit-box;
 
  -webkit-box-orient: vertical;
 
  -webkit-line-clamp: 1;
 
  overflow: hidden;
 
}
 
 
 
.author {
 
  color: #777777;
 
  font-size: 30rpx;
 
  //间距
 
  margin-top: 50rpx;
 
  display: inline-block;
 
}
 
 
 
.category {
 
  border: 1px solid gray;
 
  float: right;
 
  color: gray;
 
  font-size: 25rpx;
 
  padding: 2rpx 15rpx;
 
  margin-top: 50rpx;
 
}
 
</style>