VUE小细节杂项整理

此文档主要整理一些不常用的,且常被遗忘掉的知识点

 

一、${}方法的使用:用于在字符串内绑定数据

常规字符串内绑定数据方法:

<div :id="'a' + count"></div>

利用${}方法:

// 注意:`号不是单引号
// ${变量}
<div :id="`a${count}`"></div>

 

 

二、事件函数默认自带$event参数:

<template>
    <input type="text" v-model="count" @input="test"/>
</template>

<script setup>
    import {
        ref
    } from 'vue'

    const count = ref(123)
    
    const test = $event=>{
        console.log($event.detail.value);
    }
</script>

 

 

三、绑定动态属性、动态事件:

<!-- 动态属性 -->
<a :[attributeName]="url"> ... </a>
// attributeName 返回值应用: null 或 string,且字符串为小写(因为浏览器会强制将大写转小写)。 <!-- 动态事件 --> <a @[eventName]="doSomething">
// eventName 返回值应用: null 或 string,且字符串为小写(因为浏览器会强制将大写转小写)。

 

警告:复杂的动态参数建议采用计算属性,比如以下方式不建议采用:

<!-- 这会触发一个编译器警告 -->
<a :['foo' + bar]="value"> ... </a>

 

 

四、DOM更新机制:nextTick()

响应式数据更新之后,DOM并不是同步更新。DOM是在下一个更新周期才同步更新。由于这个更新周期比较快,我们以为他们是同步的。

我们可以使用nextTick()解决这个问题,详见:https://www.cnblogs.com/wm218/p/16702291.html

 

五、v-show 不支持在 <template> 元素上使用

 

六、当 v-if 和 v-for 同时存在于一个元素上的时候,v-if 会首先被执行。但是我们不推荐同时使用这二个。

 

七、v-for内的解勾操作方法:

<template>
    <!-- 不解勾,要调用属性访问 item.name -->
    <div v-for="(item, index) in lists">第 {{index + 1}}个学生:{{item.name}}</div>

    <!-- 解勾直接使用 name -->
    <div v-for="({name, age}, index) in lists">第 {{index + 1}}个学生:{{name}}</div>
</template>

<script setup>
    import {
        ref
    } from 'vue'

    const lists = ref([
        {
            id: 1,
            name: '张三',
            age: 15
        },{
            id: 2,
            name: '李四',
            age: 14
        }
    ])
</script>

 

八、v-for中也可以使用 of 代替 in

<div v-for="item of items"></div>

 

九、v-for遍历对象

<template>
    <div v-for="(key, value, index) in obj">第{{index+1}}个属性:{{key}} : {{value}} </div>
</template>

<script setup>
    import {
        ref
    } from 'vue'

    const obj = {
            id: 1,
            name: '张三',
            age: 15
        }
</script>

 

十、<textarea>不支持插件语法,所以必需采用v-model来替代。

<!-- 错误 -->
<textarea>{{ text }}</textarea>

<!-- 正确 -->
<textarea v-model="text"></textarea>

  

十一、v-model修饰符

.lazy  默认情况下,v-model 会在每次 input 事件后更新数据 (IME 拼字阶段的状态例外)。你可以添加 lazy 修饰符来改为在每次 change 事件后更新数据:

.number 让用户输入自动转换为数字。

1、如果该值无法被 parseFloat() 处理,那么将返回原始值

2、number 修饰符会在输入框有 type="number" 时自动启用。 

.trim 自动去除用户输入内容中两端的空格

 

十二、ref 操作Dom实例

访问单个实例

<script setup>
import { ref, onMounted } from 'vue'

// 声明一个 ref 来存放该元素的引用
// 必须和模板里的 ref 同名
const input = ref(null)

onMounted(() => {
  input.value.focus()   // 注意,只能在挂载之后获取DOM。而且采用的是.value方式获取实例
})
</script>

<template>
  <input ref="input" />
</template>

 

访问多个动态实例

<script setup>
import { ref, onMounted } from 'vue'

const list = ref([
  /* ... */
])
// 由于不确定实例,所以这里采用数组 const itemRefs
= ref([]) onMounted(() => console.log(itemRefs.value)) </script> <template> <ul> <li v-for="item in list" ref="itemRefs"> <!-- 注意这里写法 --》 {{ item }} </li> </ul> </template>

 

 

十三、组件命名:在单文件中(SFC),建议组件命名采用 PascalCase 形式,以此区分HTML标签。虽然HTML标签不区分大小写,但Vue单文件在编译中区分大小写。

 

十四、事件、属性名建议采用 kebab-case 全小写形式。在定义prpos或emits时,采用驼峰  camelCase  写法。

 

十五、建议采用 <my-component></my-component> 这种方式闭合组件,而不是<my-component />

 

十六、某些 HTML 元素对于放在其中的元素类型有限制,例如 <ul>,<table> ,相应的,某些元素仅在放置于特定元素中时才会显示,例如 <li>,<tr>。

比如以下输出将会出错:

<table>
  <blog-post-row></blog-post-row>
</table>

解决方案:

<table>
  <tr is="vue:blog-post-row" v-for="(item,index) in lists" :title="item.title"></tr>
</table>

 

十七、defineProps() 配置中default(){...}或validator(){...} 内不可以访问 <script setup> 中定义的其他变量,因为在编译时整个表达式都会被移到外部的函数中。

 

十八、组件Attributes继承规则:

默认情况下,除props、emits之外的属性会附加到组件根节点上,比如:

<!-- 组件test.vue 内代码 -->
<div>我是test组件</div>

<!-- 页面调用 test组件代码 -->
<test id="a1"></test>

<!-- 实际test.vue 渲染结果为 -->
<div id="a1">我是test组件</div>

SO,如果组件没有根节点时,我们想把除props、emits之外的属性会附加到指定元素上,可用: v-bind = $attrs 的方式,如下:

<!-- 组件test.vue 内代码 -->
<div>我是test组件</div>
<div v-bind=$attrs>属性要加在这上面</div>
<div>我是test组件</div>

<!-- 页面调用 test组件代码 -->
<test id="a1"></test>

<!-- 实际test.vue 渲染结果为 -->
<div>我是test组件</div>
<div id="a1">属性要加在这上面</div>
<div>我是test组件</div>

 

十九、访问组件透传 Attributes。

useAttrs()
说明:获有除props、emits内定义的所有属性
返回:[Object]
<script setup>
import { useAttrs } from 'vue'

const attrs = useAttrs()
</script>

 

二十:书写规范:

一、组件名为多个单词必要

二、Prop 定义应尽量详细

三、始终以 key 配合 v-for。

四、永远不要在一个元素上同时使用 v-if 和 v-for。

五、组件的css样式,尽量使用 scoped、module或者指定class名称的样式。

六、不要将多个组件整合在一个文件内。要把每个组件单独分成文件。

七、组件文件命令建议使用一种方式,要么全是:PascalCase,要么是kebab-case。
不要有的是PascalCase,有的是kebab-case。

八、应用特定样式和约定的基础组件 (也就是展示类的、无逻辑的或无状态的组件) 应该全部以一个特定的前缀开头,比如 Base、App 或 V。
比如: 
components/
|- AppButton.vue
|- AppTable.vue
|- AppIcon.vue

九、只应该拥有单个活跃实例的组件应该以 The 前缀命名,以示其唯一性。
这些组件永远不接受任何 prop ,比如:
components/
|- TheHeading.vue
|- TheSidebar.vue

十、与父组件紧密耦合的子组件应该以父组件名作为前缀命名。
这样做的好处是:可以把相关联的文件排放在一起。
components/
|- SearchSidebar.vue
|- SearchSidebarNavigation.vue

十一、组件名称应该以高阶的 (通常是一般化描述的) 单词开头,并以描述性的修饰词结尾。
这样做的好处是:快速了解该组件的意义
components/
|- SearchButtonClear.vue
|- SearchButtonRun.vue
|- SearchInputQuery.vue
|- SearchInputExcludeGlob.vue
|- SettingsCheckboxTerms.vue
|- SettingsCheckboxLaunchOnStartup.vue

十二、在单文件组件、字符串模板和 JSX 中,没有内容的组件应该是自闭合的——但在 DOM 模板里永远不要这样做。

十三、对于绝大多数项目来说,在单文件组件和字符串模板中,组件名称应该始终是 PascalCase 的——但是在 DOM 模板中是 kebab-case 的。

十四、组件名称应该倾向于完整的单词,而不是缩写。

十五、在声明 prop 的时候,其命名应该始终使用 camelCase,而在模板和 JSX 中应该始终使用 kebab-case。

十六、多个 attribute 的元素应该分多行撰写,每个 attribute 一行。

十七、指令缩写 (用 : 表示 v-bind:,@ 表示 v-on: 和用 # 表示 v-slot) 应该要么始终使用,要么始终不使用。

十八、单文件组件应始终保持 <script><template><style> 标签的顺序一致。且 <style> 要放在最后,因为另外两个标签至少会有一个。

十九、自定义组件的命名要采用:kebab-case

 

二十一、import 同一文件时,export 之外部份只执行一次。且此文件全局数据是共享的。示例:

被引入的文件:t.js

export {
    t,
    o
}

// 这个数据全APP中同步
var ___refreshTime = 30000;

// 在首次加载时执行。第二次加载不执行
console.log(333);


function t(v) {
    ___refreshTime = v
}

function o() {
    console.log(___refreshTime);
}

 主页面

<template>
    <button @click="to">子页面看修改的后值</button>
</template>

<script setup>
    import {
        ref,
        readonly
    } from 'vue'
    
    import {t, o} from '@/common/js/t.js'
    
    t(123) // 修改了值
    o() // 显示修改后值
    
    function to(){
        uni.navigateTo({
            url: '/pages/test/test', 
        });
    }
    
</script>

去子页面: test.vue 查看数据是否共享:

<script setup>
       import {t, o} from '@/common/js/t.js'
        o() // 打印结果,是上一个页面修改后的值
</script>

 

二十三、为兼容nvue,我们对所有js的路径引入,统一采用 @开头。即 import $array from ‘@/common/js/array.js’ 同时js内部也是采用这一规则。因为 nvue引入时必需使用@

 

二十四、defineProps 除了可以给子组件传递数组外,单页面还可以通过它获取GET形参,如下:

主页代码:

uni.navigateTo({
    url: '/pages/test/test?uid=12',  // 打开test页面,并传递 uid形参
});

 test.vue 中接收形参代码:

<script setup>
    const { uid } = defineProps({
        uid: {
            type: String
        }
    })

    console.log(uid); // 成功接收形参值
</script>

 也可以通过onLoad事件接收GET参数:

    import {
        onResize,
        onLoad
    } from '@dcloudio/uni-app'
    
    onLoad((e)=>{
        console.log(e.uid);
    })

 

posted @ 2022-09-17 16:43  1024记忆  阅读(113)  评论(0)    收藏  举报