Vue 中使用JSX練習(xí)

Vue中使用JSX練習(xí)

目標(biāo): 實(shí)現(xiàn)一個(gè)組件, 組件掛載到 APP.vue中, 在業(yè)務(wù)組件中可以向該組件傳遞dom, 并實(shí)現(xiàn)雙向綁定, 一般該組件應(yīng)該為一個(gè)輕量的模糊彈出層

App.vue

<template>
  <div id="app">
    <router-view />
    <layer v-model="_layerData"></layer>
  </div>
</template>

<script>
import layer from '@/components/layer.js'
import { mapState, mapMutations } from 'vuex'

export default {
  name: 'app', // 組件名稱
  components: { layer },
  filters: { // 過濾器
  },
  computed: { // 計(jì)算屬性
    ...mapState(['layerData']),
    _layerData: {
      get () {
        return this.layerData
      },
      set (val) {
        this.setLayer(val)
      }
    }
  },
  watch: { // 監(jiān)聽屬性
  },
  data () {
    return {
      /*
      * 頁面狀態(tài)
      * */

      /*
      * 頁面數(shù)據(jù)
      * */
    }
  },
  methods: {
    ...mapMutations(['setLayer'])
  },
  beforeCreate () { // 播放加載動(dòng)畫
  },
  created () { // 結(jié)束加載動(dòng)畫, 發(fā)起異步請(qǐng)求
  },
  mounted () { // DOM構(gòu)建完成, 即將顯示頁面
  },
  updated () { // view重新渲染, 數(shù)據(jù)更新
  },
  beforeDestroy () { // 組件實(shí)例銷毀之前
  }

}
</script>

<style>
#app {
  font-family: "Helvetica Neue", Helvetica, "PingFang SC", "Hiragino Sans GB",
  "Microsoft YaHei", "微軟雅黑", Arial, sans-serif;
}
</style>

Store.js

import Vue from 'vue'
import Vuex from 'vuex'

import home from '@/store/modules/home'

Vue.use(Vuex)

export default new Vuex.Store({
  state: {
    layerData: {}
  },
  mutations: {
    setLayer (state, payload) {
      if (payload !== '') {
        state.layerData = { ...state.layerData, ...payload }
      } else {
        state.layerData = payload
      }
    }
  },
  actions: {
  },
  modules: {
    home
  }
})

Home.vue (業(yè)務(wù)組件)

<template>
  <div class="home">
    <button @click="setTimeoutClick">打開彈出框</button>
  </div>
</template>

<script>
import { mapMutations } from 'vuex'

export default {
  name: 'home', // 組件名稱
  components: {},
  props: [], // 組件參數(shù)
  model: { // 用于 props 綁定父級(jí) v-model
  },
  filters: { // 過濾器
  },
  computed: { // 計(jì)算屬性
  },
  watch: { // 監(jiān)聽屬性
  },
  data () {
    return {
      /*
      * 頁面狀態(tài)
      * */

      /*
      * 頁面數(shù)據(jù)
      * */
    }
  },
  methods: {
    ...mapMutations(['setLayer']),
    setTimeoutClick () {
      this.handleClick()
      setTimeout(() => {
        this.handleClick()
      }, 1000)
    },
    handleClick () {
      new Promise((resolve, reject) => {
        // 定義 內(nèi)容DOM (Vue-cli2寫法中, 沒有 v-model綁定, 需要自己實(shí)現(xiàn), vue-cli4可以直接使用 v-model)
        const contentRender = function (h, context) {
          return <div>
            <div>標(biāo)題位置: {context.layerData._data.title}</div>
            <input value={context._data.inputOne} onInput={(event) => { context.myVModel(event, 'inputOne') }} />
            <br />
            <input value={context._data.inputTwo} onInput={(event) => { context.myVModel(event, 'inputTwo') }} />
            <br />
          </div>
        }
        // 定義 底部DOM
        const footerRender = function (h, context) {
          return <div>
            <button onClick={context.confirm}>確定</button>
            <button onClick={context.cancel}>取消</button>
          </div>
        }
        // 設(shè)置數(shù)據(jù)
        this.setLayer({
          contentRender,
          footerRender,
          _data: {
            title: '我的標(biāo)題啊',
            inputOne: '',
            inputTwo: ''
          },
          resolve,
          reject,
          isShow: true
        })
      })
        .then((data) => { console.log('then', data) })
        .catch((data) => { console.log('catch', data) })
    }
  },
  beforeCreate () { // 播放加載動(dòng)畫
  },
  created () { // 結(jié)束加載動(dòng)畫, 發(fā)起異步請(qǐng)求
  },
  mounted () { // DOM構(gòu)建完成, 即將顯示頁面
  },
  updated () { // view重新渲染, 數(shù)據(jù)更新
  },
  beforeDestroy () { // 組件實(shí)例銷毀之前
  }
}
</script>

<style scoped lang="scss">

</style>

Layer.js (該組件)

export default {
  name: 'layer', // 組件名稱
  components: {},
  props: ['layerData'], // 組件參數(shù)
  model: { // 用于 props 綁定父級(jí) v-model
    prop: 'layerData',
    event: 'layer-data-callback'
  },
  filters: { // 過濾器
  },
  computed: { // 計(jì)算屬性
  },
  watch: { // 監(jiān)聽屬性
  },
  data () {
    return {
      _data: {} // 用于綁定 v-model
    }
  },
  methods: {
    myVModel (event, name) {
      this._data[name] = event.target.value
    },
    isRunRender (renderFun, h, context) {
      if (typeof renderFun === 'function') {
        return renderFun(h, context)
      } else {
        return ''
      }
    },
    confirm () {
      this.layerData.resolve(this._data)
      this.resetLayer()
    },
    cancel () {
      this.layerData.reject()
      this.resetLayer()
    },
    resetLayer () {
      this.$emit('layer-data-callback', '')
      this._data = {}
    }
  },
  render (h) {
    const context = this
    const baseRender = function (h, context) {
      if (context.layerData.isShow) {
        return <div class="main">
          <div class="content">
            { context.isRunRender(context.layerData.contentRender, h, context)}
          </div>
          <div class="footer">
            { context.isRunRender(context.layerData.footerRender, h, context)}
          </div>
        </div>
      }
      return ''
    }
    return baseRender(h, context)
  },
  beforeCreate () { // 播放加載動(dòng)畫
  },
  created () { // 結(jié)束加載動(dòng)畫, 發(fā)起異步請(qǐng)求
  },
  mounted () { // DOM構(gòu)建完成, 即將顯示頁面
  },
  updated () { // view重新渲染, 數(shù)據(jù)更新
  },
  beforeDestroy () { // 組件實(shí)例銷毀之前
  }
}
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末中贝,一起剝皮案震驚了整個(gè)濱河市埃疫,隨后出現(xiàn)的幾起案子申窘,更是在濱河造成了極大的恐慌,老刑警劉巖蜜氨,帶你破解...
    沈念sama閱讀 217,542評(píng)論 6 504
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異,居然都是意外死亡暖呕,警方通過查閱死者的電腦和手機(jī)扔亥,發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 92,822評(píng)論 3 394
  • 文/潘曉璐 我一進(jìn)店門场躯,熙熙樓的掌柜王于貴愁眉苦臉地迎上來谈为,“玉大人,你說我怎么就攤上這事推盛÷透螅” “怎么了?”我有些...
    開封第一講書人閱讀 163,912評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵耘成,是天一觀的道長榔昔。 經(jīng)常有香客問我,道長瘪菌,這世上最難降的妖魔是什么撒会? 我笑而不...
    開封第一講書人閱讀 58,449評(píng)論 1 293
  • 正文 為了忘掉前任,我火速辦了婚禮师妙,結(jié)果婚禮上诵肛,老公的妹妹穿的比我還像新娘。我一直安慰自己默穴,他們只是感情好怔檩,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,500評(píng)論 6 392
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著蓄诽,像睡著了一般薛训。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發(fā)上仑氛,一...
    開封第一講書人閱讀 51,370評(píng)論 1 302
  • 那天乙埃,我揣著相機(jī)與錄音,去河邊找鬼锯岖。 笑死介袜,一個(gè)胖子當(dāng)著我的面吹牛,可吹牛的內(nèi)容都是我干的出吹。 我是一名探鬼主播遇伞,決...
    沈念sama閱讀 40,193評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場(chǎng)噩夢(mèng)啊……” “哼捶牢!你這毒婦竟也來了赃额?” 一聲冷哼從身側(cè)響起,我...
    開封第一講書人閱讀 39,074評(píng)論 0 276
  • 序言:老撾萬榮一對(duì)情侶失蹤叫确,失蹤者是張志新(化名)和其女友劉穎跳芳,沒想到半個(gè)月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體竹勉,經(jīng)...
    沈念sama閱讀 45,505評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡飞盆,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,722評(píng)論 3 335
  • 正文 我和宋清朗相戀三年,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片吓歇。...
    茶點(diǎn)故事閱讀 39,841評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡孽水,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出城看,到底是詐尸還是另有隱情女气,我是刑警寧澤,帶...
    沈念sama閱讀 35,569評(píng)論 5 345
  • 正文 年R本政府宣布测柠,位于F島的核電站炼鞠,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏轰胁。R本人自食惡果不足惜谒主,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,168評(píng)論 3 328
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望赃阀。 院中可真熱鬧霎肯,春花似錦、人聲如沸榛斯。這莊子的主人今日做“春日...
    開封第一講書人閱讀 31,783評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽驮俗。三九已至懂缕,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間意述,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 32,918評(píng)論 1 269
  • 我被黑心中介騙來泰國打工吮蛹, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留荤崇,地道東北人。 一個(gè)月前我還...
    沈念sama閱讀 47,962評(píng)論 2 370
  • 正文 我出身青樓潮针,卻偏偏與公主長得像术荤,于是被迫代替她去往敵國和親。 傳聞我的和親對(duì)象是個(gè)殘疾皇子每篷,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,781評(píng)論 2 354

推薦閱讀更多精彩內(nèi)容