ant-design-vue/components/_util/ContainerRender.jsx
2018-10-10 13:43:10 +08:00

95 lines
2.2 KiB
Vue

import Vue from 'vue'
import PropTypes from './vue-types'
export default {
props: {
autoMount: PropTypes.bool.def(true),
autoDestroy: PropTypes.bool.def(true),
visible: PropTypes.bool,
forceRender: PropTypes.bool.def(false),
parent: PropTypes.any,
getComponent: PropTypes.func.isRequired,
getContainer: PropTypes.func.isRequired,
children: PropTypes.func.isRequired,
},
mounted () {
if (this.autoMount) {
this.renderComponent()
}
},
updated () {
if (this.autoMount) {
this.renderComponent()
}
},
beforeDestroy () {
if (this.autoDestroy) {
this.removeContainer()
}
},
methods: {
removeContainer () {
if (this.container) {
this._component && this._component.$destroy()
this.container.parentNode.removeChild(this.container)
this.container = null
}
},
renderComponent (props = {}, ready) {
const { visible, forceRender, getContainer, parent } = this
const self = this
if (visible || parent.$refs._component || forceRender) {
let el = this.componentEl
if (!this.container) {
this.container = getContainer()
el = document.createElement('div')
this.componentEl = el
this.container.appendChild(el)
}
if (!this._component) {
this._component = new Vue({
data: {
comProps: props,
},
parent: self.parent,
el: el,
mounted () {
this.$nextTick(() => {
if (ready) {
ready.call(self)
}
})
},
updated () {
this.$nextTick(() => {
if (ready) {
ready.call(self)
}
})
},
render () {
return self.getComponent(this.comProps)
},
})
} else {
this._component.comProps = props
}
}
},
},
render () {
return this.children({
renderComponent: this.renderComponent,
removeContainer: this.removeContainer,
})
},
}