zoukankan      html  css  js  c++  java
  • (十九)小程序的前端【首页】页面和后端逻辑

    前端【首页】页面

    思路

    1.初始化数据
    2.下拉刷新数据
    3.上翻页刷新数据
    4.瀑布流-----在wxss中 falls
    <!-- 上面四幅图 -->
    <view class="menu">
      <view class="item" wx:for="{{menuList}}" wx:key="index">
        <image src="{{item.img}}"></image>
        <text>{{item.text}}</text>
      </view>
    </view>
    <!-- news -->
    
      <view class="falls">
        <view class="item" wx:for="{{newsList}}" wx:key="id">
          <view class="pic">
            <navigator url="/pages/newsDetail/newsDetail?newsId={{item.id}}"><image class="img" src="{{item.cover}}" mode="widthFix"></image></navigator>
            <view class="user">
              <view class="author">
                <image class="avatar" src="{{item.user.avatar}}"></image>
                <view>{{item.user.nickname}}</view>
              </view>
              <view class="favor">
                <image class="icon" src="/static/images/icon/likes_smallicon_nor.png"></image>
                <view>{{item.favor_count}}</view>
              </view>
            </view>
          </view>
    
          <view class="title">
            <text>{{item.content}}</text>
            <text class="tag" wx:if="{{item.topic.title}}"># {{item.topic.title}}</text>
          </view>
        </view>
      </view>
    前端wxml
    /**index.wxss**/
    .menu{
      padding: 20rpx
    }
    .menu image{
       100rpx;
      height: 100rpx;
      border-radius: 50rpx;
    }
    .menu{
      display: flex;
      flex-direction: row;
      justify-content: space-around;
    }
    
    .menu .item{
      display: flex;
      flex-direction: column;
      align-items: center;
    }
    
    
    .falls
    {
        -moz-column-count:2; /* Firefox */
        -webkit-column-count:2; /* Safari and Chrome */
        column-count:2;
    
        -moz-column-gap:20rpx; /* Firefox */
        -webkit-column-gap:20rpx; /* Safari and Chrome */
        column-gap:20rpx;
    }
    .falls .item{
      break-inside: avoid-column;
      -webkit-column-break-inside: avoid; /* Safari and Chrome */
    }
    
    .falls .item .pic{
      position: relative;
    }
    
    .falls .item .pic .img{
       100%;
      display: block;
    }
    
    .falls .item .pic .user{
      position: absolute;
      bottom: 0;
      left: 0;
      background-color: #333;
      opacity: 0.6;
      height: 60rpx;
    
      display: flex;
      flex-direction: row;
      justify-content: space-between;
      align-items: center;
       100%;
      color: #fff;
      font-size: 28rpx;
    }
    .falls .item .pic .user .author,.falls .item .pic .user .favor{
      display: flex;
      flex-direction: row;
      align-items: center;
    
      padding: 0 10rpx;
    }
    
    .falls .item .pic .user .author .avatar{
       28rpx;
      height: 28rpx;
      border-radius: 14rpx;
      margin-right:10rpx;
    }
    
    .falls .item .pic .user .favor .icon{
       28rpx;
      height: 28rpx;
      margin-right:10rpx;
    }
    
    .falls .item .title{
      border: 1rpx solid #ddd;
      padding: 15rpx;
      font-size: 28rpx;
    }
    
    .falls .item .title .tag{
      font-size: 32rpx;
      color: #00c8b6;
      margin: 0 10rpx;
    }
    前端wxss
    // pages/home/home.js
    var api = require('../../config/api.js')
    Page({
    
      /**
       * 页面的初始数据
       */
      data: {
        menuList: [{
          'text': '精品文章',
          'img': "/static/icon/home_essays_icon_show.png"
        },
        {
          'text': '小视频',
          'img': "/static/icon/home_video_icon_show.png"
        },
        {
          'text': '名人堂',
          'img': "/static/icon/home_superstar_icon_show.png"
        },
        {
          'text': '观点说',
          'img': "/static/icon/home_viewpoint_icon_show.png"
        },
        ],
        newsList: [],
        minId:0,
        maxId:0,
    
      },
    
    
      /**
       * 分页获取动态列表
       */
      getNews:function(){
        wx.request({
          url: api.News,
          method: 'GET',
          dataType: 'json',
          responseType: 'text',
          success: (res) => {
            this.setData({
              newsList:res.data,
              maxId:res.data[0].id,
              minId:res.data[res.data.length-1].id,
            })
          },
        })
      },
    
      /**
       * 生命周期函数--监听页面加载
       * 页面第一次执行执行这个函数 也可以把上面的函数写在这个函数里
       */
      onLoad: function (options) {
        this.getNews(false);
      },
      /**
       * 页面相关事件处理函数--监听用户下拉动作
       * 1. 传数据 最大的id
       * 2. 返回的数据和之前有的数据合并用 concat
       * 3. 在记录一下当前的最大的id
       */
      onPullDownRefresh: function () {
        wx.request({
          url: api.News,
          data: {
            max_id:this.data.maxId
          },
          method: 'GET',
          dataType: 'json',
          responseType: 'text',
          success: (res)=> {
            if(!res.data.length){
              wx.showToast({
                title: '已是最新数据',
                icon:"none"
              })
              // 刷新之后就停止
              wx.stopPullDownRefresh()
              return
            }
            // 查出来的数据翻转一下
            var dataList = res.data.reverse();
            this.setData({
              newsList: dataList.concat(this.data.newsList),
              maxId: dataList[0].id
            })
            wx.stopPullDownRefresh()
          },
         
        })
      },
    
      /**
       * 页面上拉触底事件的处理函数
       * 1. 传数据 最小的id
       * 2. 返回的数据和之前有的数据合并用 concat
       * 3. 在记录一下当前的最小的id
       */
      onReachBottom: function () {
        wx.request({
          url: api.News,
          data: {
            min_id:this.data.minId
          },
          method: 'GET',
          dataType: 'json',
          responseType: 'text',
          success: (res)=> {
            if(res.data.length===0){
              wx.showToast({
                title: '已经到底啦',
                icon: 'none',
              })
              return
            }
            this.setData({
              newsList:this.data.newsList.concat(res.data),
              minId:res.data[res.data.length-1].id
            })
          },
        })
      },
    })
    前端js

    后端的接口

    方式一 继承APIView

    from app01 import models
    from django.forms import model_to_dict
    from rest_framework.views import APIView
    from rest_framework import serializers
    from rest_framework.response import Response
    
    # 第二步 序列化
    class NewsModelSerializer(serializers.ModelSerializer):
        # 因为这个样子是拿到的 tpoic和user 是一个数字 我们不希望是这样 所有我们修改 

       # 下面两行代码 + 下面的两个函数 是解决方法 user = serializers.SerializerMethodField() topic = serializers.SerializerMethodField() class Meta: model = models.News fields = ['id', 'cover', 'content', 'topic', "user", 'favor_count'] def get_user(self, obj): return model_to_dict(obj.user, fields=['id', 'nickname', 'avatar']) def get_topic(self, obj): if not obj.topic: return return model_to_dict(obj.topic, fields=['id', 'title']) # 第一步 先进入这个函数 查到数据走序列化 class NewsView(APIView): def get(self, request, *args, **kwargs): min_id = request.query_params.get("min_id") max_id = request.query_params.get("max_id") if min_id: queryset = models.News.objects.filter(id__lt=min_id).order_by('-id')[0:10] elif max_id: queryset = models.News.objects.filter(id__gt=max_id).order_by('id')[0:10] else: queryset = models.News.objects.all().order_by('-id')[0:10] # GET 用instance 多条用 mang=True ser = NewsModelSerializer(instance=queryset, many=True) return Response(ser.data)

    方式二 继承ListAPIView

    from app01 import models
    from rest_framework import serializers
    from django.forms import model_to_dict
    from rest_framework.filters import BaseFilterBackend
    from rest_framework.pagination import LimitOffsetPagination
    from rest_framework.generics import ListAPIView
    from rest_framework.response import Response
    
    
    # 序列化
    class ListNewsModelSerializer(serializers.ModelSerializer):
        # 因为这个样子是拿到的 tpoic和user 是一个数字 我们不希望是这样 所有我们修改
        user = serializers.SerializerMethodField()
        topic = serializers.SerializerMethodField()
    
        class Meta:
            model = models.News
            fields = ['id', 'cover', 'content', 'topic', "user", 'favor_count']
    
        def get_user(self, obj):
         # 想要展示的几种形式
    # return obj.user.nickname # return {'nickname',obj.user.nickname} # from django.forms import model_to_dict return model_to_dict(obj.user, fields=['id', 'nickname', 'avatar']) def get_topic(self, obj): if not obj.topic: return # from django.forms import model_to_dict return model_to_dict(obj.topic, fields=['id', 'title']) # 分页 class OldBoyLimitPagination(LimitOffsetPagination): """ 本质上帮助我们进行切片的处理:[0:N] """ default_limit = 5 max_limit = 50 limit_query_param = 'limit' offset_query_param = 'offset' def get_offset(self, request): return 0 def get_paginated_response(self, data): return Response(data) class ReachBottomFilter(BaseFilterBackend):   '''下来传过来的值''' def filter_queryset(self, request, queryset, view): min_id = request.query_params.get('min_id') if not min_id: return queryset return queryset.filter(id__lt=min_id)[0:10] class PullDownRefreshFilter(BaseFilterBackend):
      '''上拉刷新'''
    def filter_queryset(self, request, queryset, view): max_id = request.query_params.get('max_id') if not max_id: return queryset return queryset.filter(id__gt=max_id)[0:10]
    # 第一步:
    class NewsView(ListAPIView): queryset = models.News.objects.all().order_by('-id')   # 上滑和下拉 条件走 filter_backends pagination_class = OldBoyLimitPagination filter_backends = [ReachBottomFilter, PullDownRefreshFilter]   # 这里的CreateNewsModel我省略了                     序列化 def get_serializer_class(self): if self.request.method == 'POST': return CreateNewsModelSerializer if self.request.method == 'GET': return ListNewsModelSerializer
  • 相关阅读:
    Max retries exceeded with ur
    DHTML【1】
    广播发送与接收
    用例图之我见
    rman catalog (rman 恢复目录)
    面试高频题:单链表的逆置操作/链表逆序
    C#3.0 语言基础扩充
    hdu 1114 Piggy-Bank(完全背包)
    VSS Get Latest Version 没有提示recursive的对话框解决
    微服务实践分享(3)服务发现
  • 原文地址:https://www.cnblogs.com/a438842265/p/12466029.html
Copyright © 2011-2022 走看看