第八章作业:简单留言板

需求分析:

留言板是一款能实现浏览留言,发表留言,删除留言和编辑留言的小程序,用户能够浏览当前的已留内容,并且能按照时间的升序来查看最新的留言内容;能够发表自己的留言内容,在留言发表页填写相关项后即可发表,并能查看到新留言内容;能够删除不需要的留言;能够修改留言内容。因此,简单留言板的功能主要为显示留言、发表留言、删除留言和编辑留言。

视图层设计:

根据功能需求分析,共设计4个页面:首页(显示留言页),发表留言页,编辑留言页和详情页。

数据库设计:

根据留言板功能,设计数据库表名为test,其中设计的字段有id(编号)、title(标题)、content(内容)、image(图像)、count(次数)5个字段,通过Bmob后端云设计。

代码实现:

应用配置:

小程序代码实现的第一步是设置整个应用的配置,示例代码如下:

// app.json
{
  "pages": [
    "pages/index/index",
    "pages/detail/detail"
  ],
  "window": {
    "backgroundTextStyle":"light",
    "navigationBarTextStyle": "black",
    "navigationBarTitleText": "小小留言板",
    "navigationBarBackgroundColor": "#3891f8"
  },
  "style": "v2",
  "componentFramework": "glass-easel",
  "lazyCodeLoading": "requiredComponents",
  "sitemapLocation": "sitemap.json"
}
// app.ts
var Bmob = require('utils/bmob.js');
Bmob.initialize("24448a34530563f1e8b73e2db1f68612","7700f543fe72f7e78c6811ffc386e54c")
App<IAppOption>({
  globalData: {},
  onLaunch() {
    // 展示本地存储能力
    const logs = wx.getStorageSync('logs') || []
    logs.unshift(Date.now())
    wx.setStorageSync('logs', logs)

    // 登录
    wx.login({
      success: res => {
        console.log(res.code)
        // 发送 res.code 到后台换取 openId, sessionKey, unionId
      },
    })
  },
})

示例代码如下:

<!--index.wxml-->
<image class="toWrite" bindtap="toAddDiary" src="../../images/add.jpg"></image>
<view class="page">
  <scroll-view lower-threshold="800" bindscrolltolower="pullUpLoad" upper-threshold="0" scroll-y="true" style="height: {{widdowHeight}}px;">
    <view class="page_bd">
      <view class="weui_panel_hd">留言列表</view>
      <view>
        <block wx:if="{{diaryList.length > 0}}">
          <navigator class="weui_media_box weui_media_box_text" wx:for="{{diaryList}}" wx:key="diaryItem" url="/pages/detail/detail?objectId={{item.objectId}}&count={{item.count}}">
            <view class="title">主题:{{item.attributes.title}}</view>
            <view class="content">留言内容:{{item.attributes.content}}</view>
            <view class="info">
              <view class="time">时间:{{item.updatedAt}}</view>
              <view class="count">浏览:{{item.attributes.count}}</view>
              <view class="operate">
                <icon type="cancel dels" size="16"></icon>
                <text class="del" catchtap="deleteDiary" data-id="{{item.objectId}}">删除</text>
                <icon type="success edits" size="16"></icon>
                <text catchtap="toModifyDiary" data-id="{{item.objectId}}" data-content="{{item.content}}" data-title="{{item.title}}">编辑</text>
              </view>
            </view>
          </navigator>
        </block>
      </view>
    </view>
  </scroll-view>
</view>
<view class="js_dialog" id="androidDialog1" style="opacity: 1;" wx:if="{{writeDiary}}">
  <view class="weui_mask"></view>
  <view class="weui_dialog weui_skin_android">
    <view class="weui_dialog_hd">
      <strong class="weui_dialog_title">添加留言</strong>
    </view>
    <form bindsubmit="addDiary" report-submit="true">
      <view class="weui_dialog_bd">
        <view class="weui_cells_title">标题</view>
        <view class="weui_cells weui_weui_cells_after_title">
          <view class="weui_cell weui_cell_input">
            <view class="weui_cell_bd">
              <input class="weui_input" name="title" placeholder="请输入标题"/>
            </view>
          </view>
        </view>
        <view class="weui_cells_title">留言内容</view>
        <view class="weui_cells weui_cells_after_title">
          <view class="weui_cell">
            <view class="weui_cell_bd">
              <textarea class="weui_textarea" name="content" placeholder="请输入留言内容" style="height: 3.3em;"></textarea>
              <view class="weui_textarea_counter">0/200</view>
            </view>
          </view>
        </view>
        <view class="pic">
          <view class="pictext" bindtap="uppic">添加图片</view>
          <block wx:if="{{isTypeof(url)}}">
            <image src="../../images/plus.jpg"></image>
          </block>
          <block wx:else>
            <image src="{{url}}"></image>
          </block>
        </view>
      </view>
      <view class="weui_dialog_ft">
        <view class="weui_dialog_btn weui_dialog_btn_default" bindtap="noneWindows">取消</view>
        <button loading="{{loading}}" class="weui_dialog_btn weui_dialog_btn_primary" form-type="submit">提交</button>
      </view>
    </form>
  </view>
</view>
<view class="js_dialog" id="androidDialog2" style="opacity: 1;" wx:if="{{modifyDiarys}}">
  <view class="weui_mask"></view>
  <view class="weui_dialog weui_skin_android">
    <view class="weui_dialog_hd">
      <strong class="weui_dialog_title">修改留言</strong>
    </view>
    <form bindsubmit="modifyDiary">
      <view class="weui_dialog_bd">
        <view class="weui_cells_title">标题</view>
        <input class="weui_input" name="title" value="{{nowTitle}}" placeholder="请输入标题"/>
        <view class="weui_cells_title">留言内容</view>
        <view class="weui_cells weui_cells_after_title">
          <view class="weui_cell">
            <view class="weui_cell_bd">
              <textarea class="weui_textarea" name="content" value="{{nowContent}}" placeholder="请输入留言内容" style="height: 3.3em;"></textarea>
              <view class="weui_textarea_counter">0/200</view>
            </view>
          </view>
        </view>
      </view>
      <view class="weui_dialog_ft">
        <view class="weui_dialog_btn weui_dialog_btn_default" bindtap="noneWindows">取消</view>
        <button loading="{{loading}}" class="weui_dialog_btn weui_dialog_btn_primary" form-type="submit">提交</button>
      </view>
    </form>
  </view>
</view>
/* style.wxss */

/* Global Styles */
.page {
  position: relative;
}

.page .toWrite {
  position: fixed;
  bottom: 20px;
  right: 20px;
  z-index: 9999;
  width: 60px;
  height: 60px;
}

.page .weui_panel_hd {
  font-size: 20px;
  font-weight: bold;
  padding: 20px;
}

/* Diary List Styles */
.weui_media_box {
  display: block;
  padding: 20px;
  background-color: #f9f9f9;
  border-bottom: 1px solid #ccc;
  text-decoration: none;
  color: #333;
}

.weui_media_box:hover {
  background-color: #e9e9e9;
}

.title {
  font-size: 18px;
  font-weight: bold;
  margin-bottom: 5px;
}

.content {
  font-size: 16px;
  margin-bottom: 10px;
}

.info {
  display: flex;
  justify-content: space-between;
  align-items: center;
  font-size: 14px;
}

.time,
.count {
  margin-right: 10px;
}

.operate {
  display: flex;
  align-items: center;
}

.icon,
.text {
  margin-right: 5px;
  cursor: pointer;
}

/* Dialog Styles */
.js_dialog {
  position: fixed;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  z-index: 9998;
}

.weui_mask {
  position: absolute;
  top: 0;
  left: 0;
  right: 0;
  bottom: 0;
  background-color: rgba(0, 0, 0, 0.6);
}

.weui_dialog {
  position: absolute;
  left: 50%;
  top: 50%;
  transform: translate(-50%, -50%);
  background-color: #fff;
  border-radius: 5px;
  width: 80%;
  max-width: 400px;
}

.weui_dialog_hd {
  padding: 15px;
  text-align: center;
  border-bottom: 1px solid #e5e5e5;
}

.weui_dialog_bd {
  padding: 20px;
}

.weui_dialog_ft {
  padding: 15px;
  text-align: center;
  border-top: 1px solid #e5e5e5;
}

.weui_dialog_btn {
  display: inline-block;
  padding: 10px 15px;
  font-size: 16px;
  cursor: pointer;
  border-radius: 5px;
}

.weui_dialog_btn_default {
  color: #888;
  border: 1px solid #888;
}

.weui_dialog_btn_primary {
  color: #fff;
  background-color: #007bff;
  border: 1px solid #007bff;
}
var Bmob = require('../../utils/bmob');
var common = require('../../utils/common');
var app = getApp();
var that;
var url = '';

function getList(t) {
  that = t;
  var Diary = Bmob.Object.extend("test");
  var query = new Bmob.Query(Diary);
  var query1 = new Bmob.Query(Diary);
  query.descending('createdAt');
  query.include("own");
  query.limit(that.data.limit);
  var mainQuery = Bmob.Query.or(query, query1);
  mainQuery.find({
    success: function (results) {
      console.log("查询成功,结果为:", results);
      that.setData({
        diaryList: results
      });
    },
    error: function (error) {
      console.log("查询失败:" + error.code + "--" + error.message);
    }
  });
}

Page({
  data: {
    writeDiary: false,
    loading: false,
    windowHeight: 0,
    windowWidth: 0,
    limit: 10,
    diaryList: [],
    modifyDiarys: false
  },
  onShow: function () {
    getList(this);
    wx.getSystemInfo({
      success: (res) => {
        this.setData({
          windowHeight: res.windowHeight,
          windowWidth: res.windowWidth
        });
      }
    });
  },
  toAddDiary: function () {
    this.setData({
      writeDiary: true
    });
  },
  uppic: function () {
    var that = this;
    wx.chooseImage({
      count: 1,
      sizeType: ['compressed'],
      sourceType: ['album', 'camera'],
      success: function (res) {
        var tempFilePaths = res.tempFilePaths;
        if (tempFilePaths.length > 0) {
          var newDate = new Date();
          var newDateStr = newDate.toLocaleDateString();
          var tempFilePath = [tempFilePaths[0]];
          var extension = /\.([^.]*)$/.exec(tempFilePath[0]);
          if (extension) {
            extension = extension[1].toLowerCase();
          }
          var name = newDateStr + '.' + extension;
          var file = new Bmob.File(name, tempFilePaths);
          file.save().then(
            function (res) {
              console.log(res.url());
              url = res.url();
              that.setData({
                url: url
              });
            },
            function (error) {
              console.log(error);
            }
          );
        }
      }
    });
  },
  addDiary: function (event) {
    var title = event.detail.value.title;
    var content = event.detail.value.content;
    var formId = event.detail.formId;
    console.log("event", event);
    if (!title) {
      common.showTip("标题不能为空", "loading");
    } else if (!content) {
      common.showTip("内容不能为空", "loading");
    } else {
      this.setData({
        loading: true
      });
      var currentUser = Bmob.User.current();
      var User = Bmob.Object.extend("_User");
      var UserModel = new User();
      var Diary = Bmob.Object.extend("test");
      var diary = new Diary();
      diary.set("title", title);
      diary.set("formId", formId);
      diary.set("content", content);
      diary.set("image", url);
      diary.set("count", 1);
      if (currentUser) {
        UserModel.id = currentUser.id;
        diary.set("own", UserModel);
      }
      diary.save(null, {
        success: function (result) {
          common.showTip("添加日记成功");
          that.setData({
            writeDiary: false,
            loading: false
          });
          that.onShow();
        },
        error: function (result, error) {
          common.showTip("添加留言失败,请重新发布", "loading");
        }
      });
    }
  },
  deleteDiary: function (event) {
    var that = this;
    var objectId = event.target.dataset.id;
    wx.showModal({
      title: "操作提示",
      content: "确定要删除留言?",
      success: function (res) {
        if (res.confirm) {
          var Diary = Bmob.Object.extend("test");
          var query = new Bmob.Query(Diary);
          query.get(objectId, {
            success: function (object) {
              object.destroy({
                success: function (deleteObject) {
                  console.log("删除留言成功");
                  getList(that);
                },
                error: function (object, error) {
                  console.log("删除留言失败");
                }
              });
            },
            error: function (object, error) {
              console.log("查询留言失败");
            }
          });
        }
      }
    });
  },
  toModifyDiary: function (event) {
    var nowTitle = event.target.dataset.title;
    var nowContent = event.target.dataset.content;
    var nowId = event.target.dataset.id;
    this.setData({
      modifyDiarys: true,
      nowTitle: nowTitle,
      nowContent: nowContent,
      nowId: nowId
    });
  },
  modifyDiary: function (e) {
    var t = this;
    this.modify(t, e);
  },
  modify: function (t, e) {
    var that = t;
    var modyTitle = e.detail.value.title;
    var modyContent = e.detail.value.content;
    var objectId = e.detail.value.id;
    var thatTitle = that.data.nowTitle;
    var thatContent = that.data.nowContent;
    if ((modyTitle != thatTitle || modyContent != thatContent)) {
      if (modyTitle == "" || modyContent == "") {
        common.showTip("标题或内容不能为空", "loading");
      } else {
        console.log(modyContent);
        var Diary = Bmob.Object.extend("test");
        var query = new Bmob.Query(Diary);
        query.get(that.data.nowId, {
          success: function (result) {
            result.set("title", modyTitle);
            result.set("content", modyContent);
            result.save();
            common.showTip("留言修改成功", "success", function () {
              that.onShow();
              that.setData({
                modifyDiarys: false
              });
            });
          },
          error: function (object, error) { }
        });
      }
    } else if (modyTitle == "" || modyContent == "") {
      common.showTip("标题或内容不能为空", "loading");
    } else {
      that.setData({
        modifyDiarys: false
      });
      common.showTip("修改成功", "loading");
    }
  }
});
<!--pages/detail/detail.wxml-->
<view class="page">
  <view>
    <view>
      <view>留言主题:</view>
      <view>{{rows.title}}</view>
      <view>
        <view>留言内容:</view>
        <view>{{rows.content}}</view>
        <view class="pic">
          <image src="{{rows.image}}"/>
        </view>
        <view>浏览次数:{{rows.count}}</view>
        <view>创建时间:{{rows.createAt}}</view>
      </view>
    </view>
  </view>
  <view class="footer">
    <text>Copyright @2017-2019 www.smartbull.cn</text>
  </view>
</view>
// pages/detail/detail.ts
var Bmob = require('../../utils/bmob');
Page({
  data:{
    rows:{}
  },
  onLoad:function(e){
    console.log(e);
    console.log(e.objectId);
    var objectId = e.objectId;
    var newCount = e.count;
    var that = this;
    var Diary = Bmob.Object.extend("test");
    var query = new Bmob.Query(Diary)
    query.get(objectId,{
      success:function(result){
        console.log(result);
        that.setData({
          rows:result
        })
        newCount = parseInt(newCount) + 1;
        result.set("count",newCount);
        result.save();
      },
      error:function(result,error){
        console.log("查询失败")
      }
    })
  }
})

小程序运行结果图:

 

  • 9
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值