本文是基于上一篇“網(wǎng)頁版樹莓派小車控制程序”改造而成。主要也練習(xí)了一下微信小程序的開發(fā)。這里簡(jiǎn)單記錄一下主要代碼片段。也是趟過了許多的坑,例如:微信小程序不支持完全全屏,微信小程序不能橫屏展示。所以開發(fā)過程中也用了一些非常手段。可以說這只是一個(gè)很基本的demo,所以里面很多東西,比如攝像頭監(jiān)控ip、頁面元素定位我都使用了寫死的值。特別是界面,我只是在iPhone 6上面做的實(shí)驗(yàn),所以換到其他手機(jī)上時(shí),界面就會(huì)變型了。
成都創(chuàng)新互聯(lián)公司-云計(jì)算及IDC服務(wù)提供商,涵蓋公有云、IDC機(jī)房租用、聯(lián)通服務(wù)器托管、等保安全、私有云建設(shè)等企業(yè)級(jí)互聯(lián)網(wǎng)基礎(chǔ)服務(wù),來電聯(lián)系:028-86922220
1. 基本思路
index頁面如下:

進(jìn)去之后的頁面如下(其中中間空白處會(huì)展示攝像頭監(jiān)控,不過我并沒有啟動(dòng),所以看不見):

2. 代碼結(jié)構(gòu)如下:
其中,index下面是首頁,control是控制頁面,res目錄下存放的是圖片資源

3. index目錄
index.js
//index.js
//獲取應(yīng)用實(shí)例
const app = getApp()
Page({
data: {
logo: "/res/rasp-logo.png",
welcome: "歡迎使用樹莓小車",
enterBtn: "進(jìn)入",
PromoteMsg: "Please enter the server address (eg: http://x.x.x.x:8080)",
reqURL: ""
},
// 從輸入框中獲取用戶輸入的服務(wù)器地址信息
getURL: function (e) {
this.setData({
reqURL: e.detail.value
})
},
enterClicked: function (e) {
/*
* 當(dāng)按下進(jìn)入按鈕,需要做以下事情:
* 1. 首先判斷用戶是否已經(jīng)在輸入框中輸入完整的服務(wù)器地址
* 2. 發(fā)起一個(gè)到服務(wù)器的GET請(qǐng)求,并分析服務(wù)器的響應(yīng)結(jié)果
* 3. 跳轉(zhuǎn)到小車控制界面
*/
console.log(this.data.reqURL)
if (this.data.reqURL == '') {
wx.showModal({
title: '提示',
content: '請(qǐng)先輸入正確的服務(wù)器地址!',
})
return
}
// 發(fā)起到服務(wù)器的GET請(qǐng)求
wx.request({
url: this.data.reqURL,
success: function (res) {
// 在這里獲取POST請(qǐng)求地址,以及視頻流地址,然后賦值給全局變量,供control頁面調(diào)用
console.log(res.data.match(/url = \"(\S*)\"/)[1])
console.log(res.data.match(/src=\"(\S*)\"/)[1])
app.globalData.postURL = res.data.match(/url = \"(\S*)\"/)[1]
app.globalData.cameraURL = res.data.match(/src=\"(\S*)\"/)[1]
// 跳轉(zhuǎn)到control頁面
wx.navigateTo({
url: '/pages/control/control',
})
},
fail: function(res) {
wx.showModal({
title: '提示',
content: '請(qǐng)檢查輸入的服務(wù)器地址!',
})
}
})
}
})index.json:無數(shù)據(jù),只有一對(duì)打括號(hào)
index.wxml
<!--index.wxml-->
<view>
<view class="welcome">
<view class="logo">
<image src="{{logo}}"></image>
</view>
<view>
<text class="words">{{welcome}}</text>
</view>
</view>
<input class="requestURL" type="text" placeholder="{{PromoteMsg}}" focus='1' cursor='10' confirm-type="done" bindinput='getURL'></input>
<button class='enter' bindtap='enterClicked'>{{enterBtn}}</button>
</view>index.wxss
/**index.wxss**/
.welcome{
display: flex;
margin-top: 50rpx;
flex-direction: column;
align-items: center;
justify-content: space-between;
}
.requestURL{
margin: 50rpx 10rpx 30rpx 10rpx;
border: 1px solid gray;
font-style: italic;
font-size: small
}
.enter{
margin-right: 10rpx;
width: 150rpx;
height: 60rpx;
font-size: small
}4. control目錄
control.js
// pages/control/control.js
const app = getApp()
Page({
/**
* 頁面的初始數(shù)據(jù)
*/
data: {
// Car control images
"forwardBtn": "/res/forward.png",
"leftBtn": "/res/left.png",
"rightBtn": "/res/right.png",
"backLeftBtn": "/res/back-left.png",
"backRightBtn": "/res/back-right.png",
"backBtn": "/res/backward.png",
// Camera control images
"upBtn": "/res/forward.png",
"camLeftBtn": "/res/camLeft.png",
"camRightBtn": "/res/camRight.png",
"downBtn": "/res/backward.png",
"resetBtn": "/res/reset.png"
},
carMove: function(event) {
wx.request({
url: this.data.postURL,
data: event.currentTarget.dataset.direction,
method: "POST",
success: function(res){
},
fail: function(res){
}
})
},
carStop: function(event) {
wx.request({
url: this.data.postURL,
data: "S",
method: "POST",
success: function (res) {
},
fail: function (res) {
}
})
},
camMove: function(event) {
wx.request({
url: this.data.postURL,
data: event.currentTarget.dataset.direction,
method: "POST",
success: function (res) {
},
fail: function (res) {
}
})
},
/**
* 生命周期函數(shù)--監(jiān)聽頁面加載
*/
onLoad: function (options) {
//this.data.cameraURL = app.globalData.cameraURL
this.setData({
cameraURL: app.globalData.cameraURL,
postURL: app.globalData.postURL
})
console.log(this.data.cameraURL)
console.log("post url in control page: " + app.globalData.postURL)
},
/**
* 生命周期函數(shù)--監(jiān)聽頁面初次渲染完成
*/
onReady: function () {
},
/**
* 生命周期函數(shù)--監(jiān)聽頁面顯示
*/
onShow: function () {
//console.log(wx.getSystemInfoSync().windowWidth)
//console.log(wx.getSystemInfoSync().windowHeight)
},
/**
* 生命周期函數(shù)--監(jiān)聽頁面隱藏
*/
onHide: function () {
},
/**
* 生命周期函數(shù)--監(jiān)聽頁面卸載
*/
onUnload: function () {
},
/**
* 頁面相關(guān)事件處理函數(shù)--監(jiān)聽用戶下拉動(dòng)作
*/
onPullDownRefresh: function () {
},
/**
* 頁面上拉觸底事件的處理函數(shù)
*/
onReachBottom: function () {
},
/**
* 用戶點(diǎn)擊右上角分享
*/
onShareAppMessage: function () {
}
})control.json
{
"navigationBarBackgroundColor": "#ffffff",
"navigationBarTextStyle": "black",
"navigationBarTitleText": "樹莓小車",
"backgroundColor": "#eeeeee",
"backgroundTextStyle": "light",
"enablePullDownRefresh": false,
"navigationStyle": "custom",
"disableScroll": true
}control.wxml
<!--pages/control/control.wxml-->
<view class='control'>
<!-- This image shows the camera view -->
<image class='cameraView' src='http://192.168.1.104:8080/?action=stream' ></image>
<!-- The following six images control the car move -->
<image class='button' id='forward' src='{{forwardBtn}}' bindtouchstart='carMove' data-direction='F' bindtouchend='carStop'></image>
<image class='button' id='left' src='{{leftBtn}}' bindtouchstart='carMove' data-direction='L' bindtouchend='carStop'></image>
<image class='button' id='right' src='{{rightBtn}}' bindtouchstart='carMove' data-direction='R' bindtouchend='carStop'></image>
<image class='button' id='backLeft' src='{{backLeftBtn}}' bindtouchstart='carMove' data-direction='BL' bindtouchend='carStop'></image>
<image class='button' id='backRight' src='{{backRightBtn}}' bindtouchstart='carMove' data-direction='BR' bindtouchend='carStop'></image>
<image class='button' id='back' src='{{backBtn}}' bindtouchstart='carMove' data-direction='B' bindtouchend='carStop'></image>
<!-- The following images control the camera move -->
<image class='button' id='up' src='{{upBtn}}' bindtouchstart='camMove' data-direction='VU'></image>
<image class='button' id='camLeft' src='{{camLeftBtn}}' bindtouchstart='camMove' data-direction='HL'></image>
<image class='button' id='camRight' src='{{camRightBtn}}' bindtouchstart='camMove' data-direction='HR'></image>
<image class='button' id='down' src='{{downBtn}}' bindtouchstart='camMove' data-direction='VD'></image>
<image class='button' id='reset' src='{{resetBtn}}' bindtouchstart='camMove' data-direction='RESET'></image>
</view>control.wxss
/* pages/control/control.wxss */
.control {
width: 100%;
height: 100%;
transform: rotate(90deg);
background-color: #eee;
justify-content: center;
}
.cameraView {
margin-left: 0px;
width: 603px;
height: 375px;
background-color: #eee;
justify-content: center;
}
.button {
height: 60px;
width: 60px;
opacity: 0.3;
}
#forward {
left: 60px;
top: 135px;
}
#left {
left: 0px;
top: 195px;
}
#right {
left: 120px;
top: 195px;
}
#backLeft {
left: 0px;
top: 255px;
}
#backRight {
left: 120px;
top: 255px;
}
#back {
left: 60px;
top: 315px;
}
#up {
left: 480px;
top: 195px;
}
#camLeft {
left: 420px;
top: 255px;
}
#camRight {
left: 540px;
top: 255px;
}
#down {
left: 480px;
top: 315px;
}
#reset{
left: 480px;
top: 135px
}5. 工程全局控制
app.js:實(shí)際似乎并沒有用到,里面都是工程創(chuàng)建時(shí)的默認(rèn)代碼
//app.js
App({
onLaunch: function () {
// 展示本地存儲(chǔ)能力
var logs = wx.getStorageSync('logs') || []
logs.unshift(Date.now())
wx.setStorageSync('logs', logs)
// 登錄
wx.login({
success: res => {
// 發(fā)送 res.code 到后臺(tái)換取 openId, sessionKey, unionId
}
})
// 獲取用戶信息
wx.getSetting({
success: res => {
if (res.authSetting['scope.userInfo']) {
// 已經(jīng)授權(quán),可以直接調(diào)用 getUserInfo 獲取頭像昵稱,不會(huì)彈框
wx.getUserInfo({
success: res => {
// 可以將 res 發(fā)送給后臺(tái)解碼出 unionId
this.globalData.userInfo = res.userInfo
// 由于 getUserInfo 是網(wǎng)絡(luò)請(qǐng)求,可能會(huì)在 Page.onLoad 之后才返回
// 所以此處加入 callback 以防止這種情況
if (this.userInfoReadyCallback) {
this.userInfoReadyCallback(res)
}
}
})
}
}
})
},
globalData: {
userInfo: null,
postURL: null,
cameraURL: null
}
})app.json:
{
"pages": [
"pages/index/index",
"pages/control/control"
],
"window": {
"backgroundTextStyle": "light",
"navigationBarBackgroundColor": "#fff",
"navigationBarTitleText": "樹莓小車",
"navigationBarTextStyle": "black",
"showStatusBar": false
}
}app.wxss:
/**app.wxss**/
.container {
height: 100%;
display: flex;
flex-direction: column;
align-items: center;
justify-content: space-between;
padding: 200rpx 0;
box-sizing: border-box;
}
project.control.json:
{
"description": "項(xiàng)目配置文件。",
"packOptions": {
"ignore": []
},
"setting": {
"urlCheck": false,
"es6": true,
"postcss": true,
"minified": true,
"newFeature": true
},
"compileType": "miniprogram",
"libVersion": "2.0.4",
"appid": "wx18414b9f85bfc895",
"projectname": "wechat-control",
"isGameTourist": false,
"condition": {
"search": {
"current": -1,
"list": []
},
"conversation": {
"current": -1,
"list": []
},
"game": {
"currentL": -1,
"list": []
},
"miniprogram": {
"current": -1,
"list": []
}
}
}以上就是本文的全部?jī)?nèi)容,希望對(duì)大家的學(xué)習(xí)有所幫助,也希望大家多多支持創(chuàng)新互聯(lián)。
名稱欄目:微信小程序?qū)崿F(xiàn)樹莓派(raspberrypi)小車控制
網(wǎng)站網(wǎng)址:http://www.chinadenli.net/article24/gjopce.html
成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供標(biāo)簽優(yōu)化、動(dòng)態(tài)網(wǎng)站、品牌網(wǎng)站制作、網(wǎng)站內(nèi)鏈、外貿(mào)網(wǎng)站建設(shè)、關(guān)鍵詞優(yōu)化
聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請(qǐng)盡快告知,我們將會(huì)在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場(chǎng),如需處理請(qǐng)聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來源: 創(chuàng)新互聯(lián)