一、新增頁(yè)面
- 在src/pages下面新建文件夾,并且新建xxx.vue/main.js/main.json文件
- app.json文件新增頁(yè)面路徑
- ctrl+c退出 npm run dev重新編譯
- xxx.vue頁(yè)面結(jié)構(gòu)
<template>
<div class="container">
// ... html 注意:template標(biāo)簽下只能有一個(gè)根元素 否則報(bào)錯(cuò)
</div>
</template>
<script>
export default{
data () {
return {
// ... 數(shù)據(jù)
}
},
methods: {
// ... 方法
}
}
</script>
<style lang="less">
// ... less 樣式
</style>
或者
<style>
// ... 普通的css樣式
</style>
- mpvue和mpvue-weui
mpvue是一個(gè)使用 Vue.js 開發(fā)小程序的前端框架??蚣芑?Vue.js 核心,mpvue 修改了 Vue.js 的 runtime 和 compiler 實(shí)現(xiàn),使其可以運(yùn)行在小程序環(huán)境中,從而為小程序開發(fā)引入了整套 Vue.js 開發(fā)體驗(yàn)。
【官網(wǎng)】http://mpvue.com/mpvue/
mpvue-weui是基于mpvue框架和小程序原生組件的基礎(chǔ)樣式庫(kù),可供快速開發(fā)。
【官網(wǎng)】https://kuangpf.com/mpvue-weui/
二、新增組件
- 在src/components下新建test.vue文件
- test.vue (與頁(yè)面結(jié)構(gòu)一致)
<template>
<div class="container">
</div>
</template>
<script>
export default {
data () {
return {
}
},
methods: {
}
}
</script>
<style lang="less">
// ... 樣式
</style>
- 使用組件
在xxx.vue頁(yè)面上使用
<script>
// ① 導(dǎo)入組件
import myTest from "@/components/test";
export default {
// ② 聲明組件
components: { myTest },
data () {
return {
// ...
}
},
}
</script>
<template>
<div class="container">
<!-- ③ 使用組件 -->
<my-test></my-test>
</div>
</template>
- 組件間的傳值
① 父組件傳值給子組件
父組件.vue
<my-test :result="resultMsg"></my-test>
// 使用:號(hào)綁定一個(gè)result屬性名,傳遞的值為父組件的resultMsg
data () {
return {
resultMsg: '我是父組件傳給子組件的值'
}
},
② 子組件接收父組件傳遞過(guò)來(lái)的值
子組件.vue
<template>
<div class="container">
<p>{{result}}</p> // ② 頁(yè)面上使用 注:如果在vue對(duì)象中使用則為this.result
</div>
</template>
export default {
// ① 通過(guò)props接收信息
// 這里props引用的是父組件在子組件上綁定的屬性名,它的值就是傳遞過(guò)來(lái)的值
props:['result'],
data () {
return {
// ...
}
},
}
- props的三種方式:
// 第一種:
props: ['result']
// 第二種:
props: {
result: String // 這里指定了字符串類型,如果類型不一致會(huì)警告的哦
}
// 第三種:
childCom: {
type: String, // 這里指定類型
default() {
return '' // 這里設(shè)置默認(rèn)值,如果父組件未傳入則使用默認(rèn)值
}
}
③ 子組件向父組件傳值
子組件.vue
// 給一個(gè)input綁定一個(gè)blur事件
<input type="text" v-model="inputValue" @blur="blurFn">
methods: {
data: function () {
return {
inputValue: ''
}
},
blurFn () {
this.$emit("changeValue", this.inputValue)
// 子組件發(fā)射自定義事件 testValue, 并且傳遞值 inputValue
// 如果要傳遞多個(gè)值,寫法為 this.$emit("事件名", 值1,值2,值3)
}
}
④ 父組件接收子組件傳遞過(guò)來(lái)的值
父組件.vue
<my-test @changeValue="parentChangeValue"></my-test>
// 父組件在子組件上使用@事件名="方法名"接收,其中事件名是子組件$emit發(fā)射的事件名
methods: {
// 在方法里定義一個(gè)接收值的函數(shù)
parentChangeValue(value){
console.log(value); // 這里的value就是子組件傳遞過(guò)來(lái)的inputValue的值
}
}
三、模板語(yǔ)法
- for循環(huán)
<ul v-for="(item, index) in list">
<li v-for="(v, i) in item"> // 注:嵌套循環(huán)需指定不同的索引
{{v.value}}
</li>
</ul>
- 條件渲染
<div v-if="type === 'A'">
A
</div>
<div v-else-if="type === 'B'">
B
</div>
<div v-else-if="type === 'C'">
C
</div>
<div v-else>
Not A/B/C
</div>
- 屬性綁定與事件綁定
<a @click.stop="chooseHome">a標(biāo)簽</a>
// 用@事件名="函數(shù)名" 綁定事件 .stop是修飾符,阻止冒泡
<button :disabled="true"></button>
<img :src="item.deviceLogo">
// 用:屬性名="變量名"綁定。注:布爾值也需要使用:號(hào)綁定,否則被視為字符串。
4.Class 與 Style 動(dòng)態(tài)綁定
<p :class="{ 'active': isActive }">xxxxx</p>
// 'active' 類名 isActive 是否綁定的判斷條件
<p :style="{ color: activeColor, fontSize: fontSize + 'px' }">xxxxx</p>
// 例: activeColor: '#ccc', fontSize: 24 轉(zhuǎn)化后
<p style="color:'#ccc';font-size: 24px;">xxxxx</p>
四、常用demo
- 上拉加載、下拉刷新
// ① 導(dǎo)入組件
import xview from "@/components/xview";
// ② 聲明組件
components: { xview,noDevices,msgModal,devModal },
// ③ 使用組件
<scroll-view class="facilist-view">
<xview @pulldownrefresh="pullDownRefresh" @scroll="scroll" @loadmore="loadmore" :refreshing="refreshing" :nomore="nomore" :hideLoadMore="hideLoadMore" ref="xview">
<ul>
<li></li>
</ul>
</xview>
</scroll-view>
// 注釋:
// pulldownrefresh 下拉刷新監(jiān)聽函數(shù) 在這個(gè)方法里做刷新列表動(dòng)作
// loadmore 上拉加載監(jiān)聽函數(shù) 在這個(gè)方法里做加載下一頁(yè)動(dòng)作
// scroll 滾動(dòng)事件 不做處理
// hideLoadMore 是否在加載完后隱藏上拉加載的文字
// ref="名稱" 可通過(guò) _this.$refs.名稱.方法名 調(diào)用組件內(nèi)部的方法
- 表單
<template>
<form @submit="formSubmit" @reset="formReset">
// ... 表單元素
<view class="section btn-wrap">
<button type="button" class="login-btn yh-btn-big" form-type="submit">登錄</button> // ... 提交按鈕
</view>
</form>
</template>
methods: {
formSubmit(e) {
console.log('form發(fā)生了submit事件,攜帶數(shù)據(jù)為:', e.mp.detail.value)
},
formReset() {
console.log('form發(fā)生了reset事件')
}
}
- modal彈層組件
xxxModal.vue 彈層組件結(jié)構(gòu)
// 彈層結(jié)構(gòu)
<template> // v-if="變量" 控制彈層顯示隱藏
<view class="modal-wrap" v-if="showModal" @touchmove.stop="preventTouchMove">
<!-- ① 遮罩層 -->
<view class="modal-mask"></view>
<!-- ② 彈出層 -->
<view class="modal-dialog message-modal-wrap">
<view class="modal-title">{{title}}</view>
<view class="modal-content">
<!-- ③ 內(nèi)容 -->
</view>
<!-- ④ 底部放關(guān)閉圖標(biāo) (也可以放按鈕) -->
<view class="modal-footer" @click="onCancel">
<img src="/static/images/modal_icon_close@2x.png" data-status="cancel" class="icon-close">
</view>
</view>
</view>
</template>
// props 接收父組件傳遞值: showModal控制顯示隱藏 title彈層標(biāo)題
props: ['showModal','title'],
// 關(guān)閉彈層事件
methods: {
preventTouchMove(){}, // 禁止屏幕滾動(dòng) 只需要一個(gè)空的函數(shù)
onCancel() {
this.$emit("hideModalFn") // 觸發(fā)父組件關(guān)閉方法(注意沒(méi)有傳遞值)
},
}
父組件.vue
// ① 導(dǎo)入彈層組件
import xxxModal from "@/components/xxxModal";
// ② 聲明組件
components: { xxxModal },
// ③ 使用組件 使用:showModal :title傳遞值給彈層組件 @hideModal接收子組件發(fā)射的事件
<xxx-modal :showModal="showModal" :title="title" @hideModalFn="hideModalFn"></xxx-modal>
// ④ data定義要傳遞的值
data () {
return {
showModal: false,
title: '提示'
}
}
// ⑤ methods里定義子組件觸發(fā)的父組件方法
methods: {
hideModalFn(){
this.$set(this.$data,'showModal',false); // 關(guān)閉彈層
}
}
// ⑥ 顯示彈層的方法
<button @click="showModalFn"></button> // 某個(gè)元素綁定showModalFn點(diǎn)擊事件
// methods里定義showModalFn方法
methods: {
showModalFn(){
this.$set(this.$data,'showModal',true); // 顯示彈層
}
}
- 滑動(dòng)刪除demo
// demo結(jié)構(gòu)
<ul>
<li v-for="(item,index) in List" :key="index" @touchstart="touchStart($event)" @touchend="touchEnd($event,index)" :data-type="item.type">
<view class="content">
// ... 展示出來(lái)的demo內(nèi)容
</view>
<div class="delect" @click="delete(index,item.id)">
刪除
</div> // 刪除按鈕,滑動(dòng)前隱藏,左滑后展示
</li>
</ul>
// 函數(shù)
methods: {
// ① 在加載列表數(shù)據(jù)時(shí)初始化滑動(dòng)屬性type
queryList(){
// 添加滑動(dòng)參數(shù)
this.List.forEach(function (item) {
this.$set(item,'type',0); // type 0 默認(rèn)沒(méi)有左滑
})
},
// ② 滑動(dòng)開始獲取startX
touchStart(e){
// 獲取移動(dòng)距離,可以通過(guò)打印出e,然后分析e的值得出
this.startX = e.mp.changedTouches[0].clientX;
},
// ③ 滑動(dòng)結(jié)束獲取endX
touchEnd(e,index){
// 獲取移動(dòng)距離
this.endX = e.mp.changedTouches[0].clientX;
// 移動(dòng)距離大于60,滑動(dòng)元素的type設(shè)為1,其它為零
if(this.startX-this.endX > 60){
for(let i=0;i<this.List.length;i++){
this.List[i].type = 0
}
this.List[index].type = 1
}
// 反向滑動(dòng)(向右)則恢復(fù)原狀
else if(this.startX-this.endX < -60){
for(let i=0;i<this.List.length;i++){
this.List[i].type = 0
}
}
},
// ④ 點(diǎn)擊回復(fù)原狀的函數(shù)(可選)
recover(index){
this.List[index].type = 0
},
// ⑤ 刪除按鈕的操作
delete(index,Id){
let _this = this;
wx.showModal({
title: '提示',
content: '確定刪除嗎?',
success(res) {
if (res.confirm) {
console.log('用戶點(diǎn)擊確定')
// 在這里發(fā)起刪除請(qǐng)求
_this.List.splice(index,1);
} else if (res.cancel) {
console.log('用戶點(diǎn)擊取消')
}
}
})
},
}
// 主要樣式
<style lang="less">
ul {
width: 100%;
li {
-webkit-transition: all 0.2s; // 動(dòng)畫過(guò)渡
transition: all 0.2s;
width: calc(~'100% + 90px'); // 這里的90px是刪除按鈕和左右間距的寬度
height: 74px;
line-height: 74px;
align-items:center;
display:flex;
.content {
width: calc(~'100% - 90px'); // 內(nèi)容區(qū)減去這個(gè)寬度
}
.delect{
width: 40px;
height: 40px;
line-height:40px;
}
&[data-type="0"]{
transform: translate3d(0,0,0); // 沒(méi)有滑動(dòng)【重要】
}
&[data-type="1"]{
transform: translate3d(-40px,0,0); // 滑動(dòng)后向左移動(dòng)40px【重要】
}
}
}
</style>
五、樣式類
公共樣式放在App.vue的
<style></style>標(biāo)簽內(nèi)模塊私有樣式放在各模塊的
<style></style>標(biāo)簽內(nèi)less常用語(yǔ)法
① 嵌套
<div class="parent">
<div class="child-one"></div>
<div class="child-two"></div>
</div>
// css寫法
.parent {
background: #f8f8f8;
margin: 0 auto;
}
.parent .child-one {
color: red;
font-size: 14px;
}
.parent .child-two {
color: blue;
font-size: 16px;
}
// less寫法
.parent {
background: #f8f8f8;
margin: 0 auto;
.child-one {
color: red;
font-size: 14px;
}
.child-two {
color: blue;
font-size: 16px;
}
}
② &的使用
<ul>
<li class="active"></li>
<li></li>
</ul>
// css 寫法
ul li {
color: #333;
}
ul li.active {
color: blue;
}
// less 寫法
ul {
li {
color: #333;
&.active { // 這里的 &.active == li.active
color: blue;
}
}
}
// 例如
li:after {
}
也可以寫成
li {
&:after {
}
}
& 向上尋找
③ calc()
// css 寫法
div {
calc(100% - 60px);
}
// less 寫法
div {
calc(~'100% - 60px');
}
④ 注釋
// less
div {
width: 100%;
height: 100%;
// color: #333;
// background: #f8f8f8; // 這兩行就被注釋掉了,不會(huì)被編譯在樣式里
margin: 0 auto;
}