本文會從產品角度來講訴如何打造一款支援表情的彈幕小程式
產品需求:演唱會應援、行走的廣告牌以及地鐵讓座提醒等等(提供一種思路)
競品分析:小程式裡的彈幕類應用大部分只支援文字,而圖片和音訊這一塊功能是缺失的
功能確定:支援滾動文字和滾動圖片
實現效果
思路:
input 獲取輸入文字,richtext顯示包含圖片的彈幕,設定richtext中文字的方向並滾動起來,滑動改變文字大小,文字顏色等操作
實現程式碼:
1.使用input輸入文字、支援emoji表情
先定義的一個"danmu"物件來儲存input輸入的彈幕文字以及彈幕樣式、
danmu: {
fontColor: "#ffffff",
text: "預設彈幕~",
fontSize: "40px",
glow: "#ffff00",
speed: '10s',
},
複製程式碼
接著定義"nodes"物件顯示資料 text:彈幕文字;fontSize:文字大小;fontColor:文字顏色;glow:文字發光;speed:滾動速度。
使用input元件輸入文字:
<input type='text'
bindconfirm='changeDanmuText'
value='{{danmu.text}}'
placeholder='輸入彈幕~'
placeholder-style='color:#fff'
cursor-spacing='28'>
</input>
複製程式碼
cursor-spacing設定input中游標與鍵盤的距離
2.richText顯示包含圖片的彈幕
定義nodes物件來更新彈幕
nodes: [{
name: 'div',
attrs: {
class: 'danmu-text'},
children: [
{
type: 'text',
text: '彈幕文字?~'},
{
name: 'img',
attrs: {
src: '網路圖片',
width: '數值',
style: '樣式'}
}
]
}],
複製程式碼
nodes的children是一個節點集合,type是型別,text型別只有text物件,預設是節點型別所以不需要type,節點型別中name是指節點名,attrs是指節點的屬性。
具體方法屬性可以看官方 richText 文件
danmu物件與rich-text元件繫結資料關係,
<rich-text nodes='{{nodes}}'
class='rich-text'
style='font-size:{{danmu.fontSize}};color:{{danmu.fontColor}};text-shadow: 0 0 20rpx {{danmu.glow}};'>
</rich-text>
複製程式碼
並更新彈幕資料在rich-text元件上
changeDanmuText: function () {
if (that.data.danmu.text != '') {
that.data.nodes[0].children = []
that.data.nodes[0].children.push({
type: 'text',
text: that.data.danmu.text
})
that.setData({
danmu: that.data.danmu,
nodes: that.data.nodes
})
}
},
複製程式碼
判斷彈幕資料,如果是有有效資料則push到children中,並立即更新資料
經過以上兩步,已經可以把input中的資料展示在rich-text中了。
滾動彈幕樣式,利用animation 的transform: translate3d,裝置會開啟GPU加速
rich-text {
width: auto;
height: auto;
display: inline-block;
}
.danmuContent {
animation: danmuAnimation 10s;
animation-iteration-count: infinite;
animation-timing-function: linear;
display: inline-block;
text-shadow: 0 0 20rpx #f00;
transform: rotate(90deg);
transform-origin: 0% 100%;
writing-mode: vertical-lr;//很重要,把文字豎著排列
text-orientation: sideways-right;//改變文字方向
}
@keyframes danmuAnimation {
from {
transform: translate3d(0, 100%, 0);
}
to {
transform: translate3d(0, -100%, 0);
}
}
複製程式碼
<view style='display:flex;align-items:center;justify-content:center;'>
<view class='danmuContent' style='min-height:{{view.height}};animation-duration:{{danmu.speed}}'>
<rich-text nodes='{{nodes}}' class='rich-text' style='font-size:{{danmu.fontSize}};color:{{danmu.fontColor}};text-shadow: 0 0 20rpx {{danmu.glow}};'>
</rich-text>
</view>
</view>
複製程式碼
下面就要插入表情和更新文字樣式
3.插入動態表情
定義動態表情url陣列gifUrl = [url0,url1,url2,....]
複製程式碼
顯示在view中
<view wx:for="{{gifUrl}}" wx:for-item="url" class='gif'>
<image src='https://user-gold-cdn.xitu.io/2018/1/13/160ef9d4a180eee1' data-gifid='https://user-gold-cdn.xitu.io/2018/1/13/160ef9d4a180eee1' bindtap='addImg' class='gif'>
</image>
</view>
複製程式碼
gifid傳到nodes中的img src裡,之後更新資料
addImg: function (e) {
that.data.nodes[0].children.push({
name: 'img',
attrs: {
src: e.currentTarget.dataset.gifid,
width: '40px',
style: 'transform:rotate(90deg)'
}
})
that.setData({
nodes: that.data.nodes,
danmu: that.data.danmu
})
},
複製程式碼
4.設定文字大小、顏色、發光以及滾動速度
這一步其實不難,主要就是互動上要簡潔、方便。
使用slider滑動改變文字大小<slider bindchange='changeFontSize'
bindchanging='changeFontSize'
show-value='true' min='10' max='200'>
</slider>
複製程式碼
文字顏色和發光顏色,使用slider模擬了一個滑動取色(這個後續文章詳細分析)
changeFontColor: function (e) {
let H = e.detail.value
let color = this.HSB2RGB([H, 1, 1])
this.data.danmu.fontColor = 'rgb(' + color.R + ',' + color.G + ',' + color.B + ')'
this.setData({
danmu: this.data.danmu
})
},
changeFontGlow: function (e) {
let H = e.detail.value
let color = this.HSB2RGB([H, 1, 1])
this.data.danmu.glow = 'rgb(' + color.R + ',' + color.G + ',' + color.B + ')'
this.setData({
danmu: this.data.danmu
})
},
複製程式碼
彈幕滾動速度同樣使用slider,取值1-3,避免太快。
<slider bindchange='changeFontSpeed'
bindchanging='changeFontSpeed' show-value='true' min='1' max='3'>
</slider>
複製程式碼
為了保持滾動速度的均勻,要根據彈幕view的高度實時改變(animation-duration),達到勻速的目的。
changeFontSpeed: function (e) {
let speedValue = e.detail.value / 4 * 100
wx.createSelectorQuery().selectAll('.danmuContent').boundingClientRect(function (rects) {
rects.forEach(function (rect) {
that.data.danmu.speed = rect.height / speedValue + 's'
that.setData({
danmu: that.data.danmu
})
})
}).exec()
},
複製程式碼
到這裡,基本功能已經實現,還有其他操作,比如保持螢幕常亮、螢幕上背景全黑並隱藏其它內容。
// 保持螢幕常亮
wx.setKeepScreenOn({
keepScreenOn: true
})
複製程式碼
設定導航欄顏色
wx.setNavigationBarColor({
frontColor: '#000000',
backgroundColor: '#000000',
})
複製程式碼
總結
滾動彈幕動畫要考慮手機的效能,沒有使用canvas,最直接就是使用css的transform動畫,效率最高。 小程式的富文字編輯支援比較弱,嘗試了許多方法,比如在文字中插入圖片,想到了類似QQ表情"[微笑/]"的方法,使用正則進行分析,再顯示在rich-text上,但是在這個專案上不合適。只好換一種思路,在文字開頭或結尾插入圖片。
以上程式碼沒做相關優化,寫的比較糙,把我的思路寫出來給大家看看,共同成長! 一個射雞獅的不歸之路~