Spare time, listen to the daughter-in-law muttered to give her to do a can express her daily mood of the small program, only she in the above hair. Since the daughter-in-law said, take some thought to do a it, because there is no UI map, all the layout depends on their own nonsense, the content is slightly longer, interested in can take in a glance.

Below will be in the form of pictures, code and we explain the implementation process of this small demo:

Home page

Home page effect picture

Home page on

  • Music (only music related codes are shown below)
<div class="bg_music" @tap="audioPlay">
    <image src=".. /.. /static/images/music_icon.png" class="musicImg" :class="isPlay? 'music_icon':''"/>
    <image src=".. /.. /static/images/music_play.png" class="music_play" :class="isPlay? 'pauseImg':'playImg'"/>
</div>
<audio id="myAudio" :src="audioUrl" autoplay loop></audio>Copy the code

data () {
  return {
    isPlay: true,
    audioCtx: ' '}},onLoad () {
  const that = this
  that.audioCtx = wx.createAudioContext('myAudio')
  that.getMusicUrl()
},
methods: {
  getMusicUrl () {
    const that = this
    const db = wx.cloud.database()
    const music = db.collection('music')
    music.get().then(res => {
      that.audioUrl = res.data[0].musicUrl
      that.audioCtx.loop = true
      that.audioCtx.play()
    })
  },
  audioPlay () {
    const that = this
    if(that.isPlay) { that.audioCtx.pause() that.isPlay = ! that.isPlay tools.showToast('You have paused music ~')}else{ that.audioCtx.play() that.isPlay = ! that.isPlay tools.showToast('Background music is on ~')}}}Copy the code

.bg_music
  position fixed
  right 0
  top 20rpx
  width 100rpx
  z-index 99
  display flex
  justify-content flex-start
  align-items flex-start
  .musicImg
    width 60rpx
    height 60rpx
  .music_icon
    animation musicRotate 3s linear infinite
  .music_play
    width 28rpx
    height 60rpx
    margin-left -10rpx
    transform-origin top
    -webkit-transform rotate(20deg)
  .playImg
    animation musicStop 1s linear forwards
  .pauseImg
    animation musicStart 1s linear forwards
#myAudio
  display noneCopy the code

1, through the wx. CreateInnerAudioContext (), for instance, the android phone music can play normally, not on IOS, the concrete reason interested can go to study;

2. Since the previous articles related to the invitation applet were sent out, the most frequently asked question was that the music could not be played, so this demo will explain the principle of implementation again.

  • The calendar

Here the calendar used a small program plug-in, the reason for putting a calendar in the home page is not too monotonous page. Here’s how the plugin works:

1. Log in to wechat public platform > Settings > Third-party Settings > Add Plug-in > Search for the name of the relevant plug-in (better search using appId) > click the right side of a plug-in to view details, enter the plug-in details page to add a plug-in, which can be added immediately.

2. The details of the plug-in generally include the use document or Git address, and the specific properties and events of the plug-in will be introduced in the document;

3. Here’s how to use plug-ins in a project:

SRC root directory app.json file, add the following content:

// "cloud": true."plugins": {
  "calendar": {
    "version": 1.1.3 ""."provider": "wx92c68dae5a8bb046"}}Copy the code

(2) Add the following content to the. Json file of the page that needs to reference the plug-in:

{
  // "navigationBarTitleText": "A Daughter-in-law's Diary.", / /"enablePullDownRefresh": true."usingComponents": {
    "calendar": "plugin://calendar/calendar"}}Copy the code

(3) Directly use the following in the page (the meaning of the specific attribute method varies according to the plug-in) :

<calendar
    :class="showCalendar? '':'hide_right'"
    class="right"
    weeks-type="en"
    cell-size="20"
    :header="showHeader"
    show-more-days=true
    calendar-style="demo4-calendar"
    board-style="demo4-board"
    :days-color="demo4_days_style"
    @dayClick="dayClick"
/>Copy the code

  • Weather and Address

(1) HERE I use Autonavi wechat small program SDK;

(2) Obtain the key value required by the relevant API as follows:

(3) Download the corresponding SDK (.js file) and introduce it into the project;

(4) Obtain weather and address through relevant API:

getWeather () {
  const that = this
  let myAmapFun = new amapFile.AMapWX({key: 'Your application key'}) myamapFun.getWeather ({success (res) {// successful callback that.address = res.livedata.city that.weather = res.livedata.weather +' '
      that.temperature = res.liveData.temperature + '℃'
      that.winddirection = res.liveData.winddirection + 'the wind' + res.liveData.windpower + 'class'}, fail (info) {/ / callback console. The failure log (info)}})},Copy the code

  • Published diary

Published here involves the text image content, most likely after submit personal small process audit will not pass, although for the first time to submit my personal little program approved, behind several audit has not been passed, although I here only limits the I and daughter-in-law can send two diaries, others not at the lower right corner of a plus sign, but reviewers will check code, Once they find any content or words related to publication in the code, it will lead to the failure of the audit. Fortunately, it has passed once, and the daughter-in-law can write something normally, which basically meets the requirements. Unfortunately, the functions related to “like” have not been updated online.

(1) Determine whether to display the release plus sign in the lower right corner of the home page through the unique openId;

(2) The functions related to uploading pictures to cloud development and storing them in database will be explained in detail later

  • Thumb up function

(1) The like function here is realized by the cloud function developed by the small program cloud, combined with the code:

<ul class="list">
    <li class="item" v-for="(item, index) in diaryList" :key="item._id" @tap="toDetail(item)">
        <image class="like" src=".. /.. /static/images/like_active.png" v-if="likeList[index] === '2'" @tap.stop="toLike(item._id, '1', item.like)"/>
        <image class="like" src=".. /.. /static/images/like.png" v-if="likeList[index] === '1'" @tap.stop="toLike(item._id, '2', item.like)"/>
        <image class="img" :src="item.url" mode="aspectFill"/>
        <p class="desc">{{item.desc}}</p>
        <div class="name-weather">
            <span class="name">{{item.name}}</span>
            <span class="weather">{{item.weather}}</span>
        </div>
        <p class="time-address">
            <span class="time">{{item.time}}</span> <! -- <span class="address">{{item.address}}</span> -->
        </p>
    </li>
</ul>
<div class="dialog" v-if="showDialog">
    <div class="box"> < H3 > Hint </h3> <p> Are you authorized to use the like function? </p> <div class="bottom">
            <button class="cancel" @tap="hideDialog"</button> <button class="confirm" lang="zh_CN" open-type="getUserInfo" @getuserinfo="login"</button> </div> </div>Copy the code

// Get the list of diariesgetDiaryList () {
  const that = this
  wx.cloud.callFunction({
    name: 'diaryList',
    data: {}
  }).then(res => {
    that.getSrcFlag = false
    that.diaryList = res.result.data.reverse()
    that.likeList = []
    that.diaryList.forEach((item, index) => {
      item.like.forEach(itemSecond => {
        if (itemSecond.openId === that.openId) {
          that.likeList.push(itemSecond.type)
        }
      })
      if (that.likeList.length < index + 1) {
        that.likeList.push('1')}}) wx. HideNavigationBarLoading () wx. StopPullDownRefresh ()})}, / / thumb up or cancel the thumb up toLike (id,type, arr) {
  const that = this
  that.tempObj = {
    id: id,
    type: type,
    like: arr
  }
  wx.getSetting({
    success (res) {
      if (res.authSetting['scope.userInfo'Wx.getuserinfo ({success:function (res) {
            that.userInfo = res.userInfo
            wx.cloud.callFunction({
              name: 'like',
              data: {
                id: id,
                type: type,
                like: arr,
                name: that.userInfo.nickName
              }
            }).then(res => {
              if (type= = ='1') {
                tools.showToast('Unliked successful')}else {
                tools.showToast('Thumbs up successful ~'That. GetOpenId ()})})}else {
        that.showDialog = true}}})}, // Login (e) {const that = this console.log(thate.tempobj, e)if (e.target.errMsg === 'getUserInfo:ok') {
    wx.getUserInfo({
      success: function (res) {
        that.userInfo = res.userInfo
        wx.cloud.callFunction({
          name: 'like',
          data: {
            id: that.tempObj.id,
            type: that.tempObj.type,
            like: that.tempObj.like,
            name: that.userInfo.nickName
          }
        }).then(res => {
          if (that.tempObj.type === '1') {
            tools.showToast('Unliked successful')}else {
            tools.showToast('Thumbs up successful ~'} // the getOpenId() method is executed to retrieve the list of entries that.getopenid ()})}})} that.showdialog =false
}Copy the code

(2) The home page gets the diary list. When storing the diary into the database set, I will add a like attribute to each diary object. The default value of like is an empty array.

(3) When the user likes or unlikes, the tempObj property of component data will temporarily store three parameters: ①, the _id of the corresponding diary; ②, the user operation type is like (like is’ 2 ‘) or unlike (unlike is’ 1 ‘); ③ The like array corresponding to the diary;

(4) Determine whether the user is authorized by wx.getSetting({}) of apPLETS API. If the user is authorized to obtain user information, the popup box will guide the user to click “CONFIRM” to manually authorize the user.

(5) After the authorization is successful and the user information is obtained, we start to call the cloud function related to “like” or “unlike”, as follows:

const cloud = require('wx-server-sdk') cloud.init() const db = cloud.database() exports.main = async (event, OpenId const wxContext = cloud.getwxContext () // Define an empty arraylet arr = []
    if(event.like && event.like.length > 0) {// Make the array defined equal to the like array under the current diary of user operations arr = event.like // define a count variableletCount = 0 // Loop over, replace the same items in the array like when openId is the same, and store the correspondingtype
      arr.forEach((item, index) => {
        if (item.openId === wxContext.OPENID) {
          count++
          arr.splice(index, 1, {
            openId: wxContext.OPENID,
            type: event.type, name: event.name})}}) // When the count variable is 0, it indicates that the user has not been stored in the like array in this diary, and the user is directly pushed and storedtype
      if (count === 0) {
        arr.push({
          openId: wxContext.OPENID,
          type: event.type,
          name: event.name
        })
      }
    } else{// If the diary like array is empty, push the current user and store ittype
      arr.push({
        openId: wxContext.OPENID,
        type: event.type, name: event.name})} // Use cloud development to operate on the relevant API of the database, i.e. update to update a certain piece of data in the collection by _idreturn await db.collection('diary').doc(event.id).update({
      data: {
        like: arr
      }
    })
  } catch (e) {
    console.error(e)
  }
}Copy the code

(6) The operation instructions of relevant cloud functions are written in the above notes, and there are unclear welcome messages. The “like” function has not been updated online (the reason is that the audit did not pass), interested people can implement this function according to the above ideas.

Published in the mood

rendering

Interpretation of the

(1) Enter the release mood page through the release plus sign in the lower right corner of the home page;

(2) Address and other related information is brought from the home page through routing;

(3) The following focuses on the operation process of uploading pictures to cloud storage and writing them into the database, as follows:

upload () {
  const that = this
  wx.chooseImage({
    count: 1,
    sizeType: ['compressed'], // You can specify whether the image is original or compressed. By default, both are availablesourceType: ['album'.'camera'], // You can specify whether the source is photo album or camera, and default to both success:function (res) {
      wx.showLoading({
        title: 'up in'}) // Returns a list of local file paths for the selected photo. TempFilePath can display the image as the SRC attribute of the IMG taglet filePath = res.tempFilePaths[0]
      const name = Math.random() * 1000000
      const cloudPath = 'picture/'+ name + filePath.match(/\.[^.]+? $/)[0] wx.cloud.uploadFile({ cloudPath, ImgUrl = res.fileId}). Then (res => {console.log(res) wx.hideloading () thate.imgurl = res.fileId}). Catch (e => { console.log('[uploading image] failed: ', e)
      })
    }
  })
},
save () {
  const that = this
  if (that.desc) {
    that.getSrcFlag = false
    const db = wx.cloud.database()
    const diary = db.collection('diary')
    if (that.imgUrl === '.. /.. /static/images/default.png') {
      that.imgUrl = '.. /.. /static/images/default.jpg'
    }
    diary.add({
      data: {
        desc: that.desc,
        time: tools.getNowFormatDate(),
        url: that.imgUrl,
        name: that.name,
        weather: that.weather,
        address: that.address,
        like: []
      }
    }).then(res => {
      wx.reLaunch({
        url: '/pages/index/main'
      })
    }).catch(e => {
      console.log(e)
    })
  } else {
    tools.showToast('Write something.')}}Copy the code

(4) The cloudPath can be defined by itself and stored in the cloud like this:

(5) We temporarily stored the manually uploaded picture path through imgUrl in component Data, and finally stored it together with the save button to the cloud database, which looks like this:


Diary Details page

Detail page rendering

Interpretation of the

(1), details will not explain more, here the use of some small program API, such as dynamic change head title, enter the dynamic random change the top title background, the number of likes is brought from the home page;

Visitors page

rendering

(1) Before authorization

(2) After authorization

The source address

Gitee.com/roberthuang…

Experience qr code

Because the daughter-in-law does not want others to see the content she wrote, has been hidden through the small program name search the small program, if you want to achieve similar functions please refer to the source code, after visitors can view the number of restrictions, here let go of the experience two-dimensional code:



Problems encountered in the demo

Some users’ avatars are empty

(1) As follows:



(2) The profile picture field is indeed empty after database viewing:


conclusion

Cloud development, although use, personal or is not recommended for large project, from the images and data loading point, the effect of the traditional server to get the data clearly much faster, since there is a free tool, I want to interested students can use up, play a small demo, new tricks, hope this article can help to students in need, Now that you’ve seen it, give it a thumbs up and go

The follow-up to optimize

juejin.cn/post/1