Я меняю свое приложение с vue 2 на vue 3. Используя составной API, я изменил свою предыдущую функцию рендеринга в этом установочном хуке. Проверив некоторую документацию, я узнал, что могу раскрывать методы с помощью context.expose({})
.
Теперь мои вопросы:
Вот мой скрипт установки:
<script>
import {h,ref,computed,provide} from 'vue';
export default {
name: 'something',
props: some props,
setup(props,context) {
const currIdx = ref(0);
const tabCnt = ref(0);
const idxMap = ref(new Map());
const idxs = ref([]);
// other variables
// computed properties
const $_size = computed(() =>{
// 1. check this.size
if (props.size) {//'medium','small'
if (props.size === 'medium') return 'medium'
if (props.size === 'small' ) return 'small'
}
// 2. check flags
if (props.medium) return 'medium'
if (props.small ) return 'small'
// 3. default value : 'medium'
return 'medium';
});
// [COMPUTED] Props normalize : SHAPE
const $_shape = computed(() =>{
// 1. check this.shape
if (props.shape) { // 'border','underline','none'
if (props.shape === 'border' ) return 'border'
if (props.shape === 'underline') return 'underline'
if (props.shape === 'none' ) return 'none'
}
// 2. check flags
if (props.border ) return 'border'
if (props.underline) return 'underline'
// x. default value : 'border'
return 'border';
});
// [COMPUTED] - [END REGION]
const getLabelNode = (props) => {
var label = props.label, idx = props.idx, disabled = !!(props.disabled || props.disable)
return h('vu-tab-label',{props:{idx, disabled}},[label]);
};
// 2. make window area -> label + navi(?)
var labelWindow = [];
labelWindow.push(h("div",{"class":"vu-tab__label-wrapper","ref":"scroll"}, labels));
if (props.navigation || props.addBtn) {
labelWindow.push(h(tabNavi))
}
// 3. do something
idxs.value = Array.from(idxMap.value.keys());
// 4. make class
let tabClass = [];
tabClass.push("vu_tab-box");
tabClass.push(`vu-tab-box--${this.$_shape}`);
// methods
const onAddClick =(e) => {
context.emit('add-tab',e);
};
context.expose({
onAddClick,
});
// x. return all nodes
return h("div",{"class":tabClass},[
h("div",{"class":"vu-tab__label-window","ref":"window"},labelWindow),
h("div",{"class":"vu-tab__content-wrapper"},contents)
]);
},
}
</script>
Что касается вопроса 1, это созданный мной хук, и я хочу выполнять эти операции внутри установки.
created() {
// 1. Check default index
if ( (this.defaultIdx === 0) || this.defaultIdx ) {
this.currIdx = this.defaultIdx;
return;
}
// 2. check slots
var slots = this.$slots['default']
if (!!slots) {
slots.find(vNode => {
if (!vNode.componentOptions) { return false }
var idx = vNode.componentOptions.propsData.idx;
if (idx === undefined) { return false }
this.currIdx = idx;
return true;
});
}
},
created
крючок в API композиции
Это просто, в API композиции нет хуков created
или beforeCreate
. Он полностью заменен на setup
. Вы можете просто запустить свой код в функции setup
напрямую или поместить его в функцию, которую вы вызываете из setup
.
Являются ли свойства выставленными с помощью expose
реактивного
Да. Хотя доступ к значениям дочерних компонентов с использованием ссылок на шаблоны на самом деле не является способом «Vue», это возможно, и переданные значения сохраняют свою реактивность. Я не смог найти никакой документации по этому вопросу, поэтому я быстро реализовал небольшую песочницу кода, чтобы попробовать. Посмотреть на себя.
https://codesandbox.io/s/falling-breeze-twetx3?file=/src/App.vue
(Если вы столкнулись с ошибкой, похожей на «Невозможно использовать импорт вне модуля», просто перезагрузите тестовую программную среду браузера в пределах, похоже, возникла проблема с шаблоном тестовой программной среды кода)