快速入门:在vue中使用tsx

如何在tsx文件中定义组件

在TSX文件中定义组件有几种常用方式:

  • 函数式组件:最简单的方式,你可以把它理解为setup函数,但是不同之处它可以直接返回JSX
export default (props, ctx) => <div>tree</div>
  • defineComponent:传递render选项,也就是Options API,这种缺点是要访问this
export default defineComponent({
  render() {
    return <div>tree</div>
  }
})
  • defineComponent:传递setup选项,利用Composition API,避免this,是推荐的形式
export default defineComponent({
  setup(props, ctx) {
    return () => <div>tree</div>
  }
})

Vue3中JSX语法

Vue3中使用tsx,借助了babel-plugin-jsx,大部分语法和react-jsx相同,除了几个Vue独有的概念:修饰符、slotdirectiveemit,因此这里仅关注这些特殊部分:

修饰符

import { withModifiers, defineComponent } from "vue";

const App = defineComponent({
  setup() {
    const count = ref(0);

    const inc = () => {
      count.value++;
    };

    return () => (
      <div onClick={withModifiers(inc, ["self"])}>{count.value}</div>
    );
  },
});

指令

指令使用需要我们转换思维,有几种不同情况:

  • 常用指令v-model,v-show跟以前用法类似,但也要注意后面是{},不是""
<input type="text" v-model={this.counter} />
  • v-if使用条件语句或三元表达式代替
<div>{ condition ?  <span>A</span> : <span>B</span> }</div>
  • v-for使用map代替
import { defineComponent, ref } from "vue";
const App = defineComponent({
  setup(){
    const list = ref<string[]>([])
    return () => {
      list.value.map((data,index) => <p key={index}>{data}</p>)
    }
  }
});

  • 自定义指令
defineComponent({
  directives: {
    focus: {
      mounted(el) {
        el.focus()
      }
    }
  },
  setup() {
    return () => <input v-focus>
  }
})

插槽

JSX中想要实现Vue中的插槽写法也有很大不同,主要利用一个叫做v-slots的指令来实现:

Parent.tsx

export default defineComponent({
  setup() {
    return () => (
      <Child
        v-slots={{
          prefix: () => <i>prefix</i>, // 具名插槽
          suffix: (props: Record<"name", string>) => <span>{props.name}</span>, // props可作插槽作用域的作用
        }}
      >
        默认插槽内容
      </Child>
    );
  },
});
const Child = defineComponent({
  setup(props, { slots }) {
    return () => (
      <>
        默认插槽: {slots.default && slots.default()}
        <br />
        具名插槽: {slots.prefix && slots.prefix()}
        <br />
        作用域插槽:{slots.suffix && slots.suffix({ name: "suffix" })}
      </>
    );
  },
});

emit

vue中子向父传值一般都是emit的方式,这个在vue3中大致写法相似,只是多了一个定义emit的步骤,这也是为了后续的类型推倒做准备。

defineComponent({
  emits: ["click"],
  setup(props ,{ emit }) {
    return () => (
      <button onClick={() => {emit("click")}}>点我触发emit</button>
    );
  },
});

  • 2
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

林多多@

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值