이 글에서는 Vue 유선형 스타일과 관련된 지식 포인트를 설명하고 관심 있는 친구들이 참고할 수 있도록 예시 코드를 공유합니다.
앞서 언급했듯이
Vue 공식 홈페이지의 스타일 가이드는 우선순위에 따라(필요, 적극 권장, 권장, 주의 사용 순) 분류되어 있으며, 코드 간격이 커서 쿼리하기 어렵습니다. 이 글은 유형별로 분류되었으며, 일부 예제나 설명은 Vue 스타일 가이드의 축약 버전입니다. , 루트 구성 요소 앱은 제외됩니다. 이렇게 하면 모든 HTML 요소 이름이 단일 단어이기 때문에 기존 및 향후 HTML 요소와의 충돌을 피할 수 있습니다
//bad Vue.component('todo', {}) //good Vue.component('todo-item', {})
[단일 파일 구성 요소 파일 이름은 항상 대문자(PascalCase)로 시작하거나 항상 줄 연결(kebab-)이어야 합니다. case)] (강력히 권장)
//bad mycomponent.vue //good MyComponent.vue //good my-component.vue
[기본 구성 요소 이름은 특정 접두사로 시작해야 합니다] (강력히 권장)
특정 스타일과 규칙을 적용하는 기본 구성 요소(즉, 논리 또는 상태 비저장 구성 요소가 없는 디스플레이 클래스)는 모두 Base, App 또는 V
//bad components/ |- MyButton.vue |- VueTable.vue |- Icon.vue //good components/ |- BaseButton.vue |- BaseTable.vue |- BaseIcon.vue
와 같은 특정 접두사로 시작합니다. 단일 활성 인스턴스만 있어야 하는 구성 요소는 고유함을 표시하기 위해 접두사 The
를 붙여 이름을 지정해야 합니다. [강력 권장]
이것은 구성 요소가 단일 페이지에서만 사용될 수 있다는 의미는 아니지만 페이지당 한 번만 사용할 수 있다는 의미입니다. 이러한 구성 요소는 어떤 prop도 허용하지 않습니다.
//bad components/ |- Heading.vue |- MySidebar.vue //good components/ |- TheHeading.vue |- TheSidebar.vue
[및 상위 구성 요소 밀접하게 결합된 하위 구성 요소는 다음과 같이 이름을 지정해야 합니다. 접두사로 상위 구성 요소 이름] (강력 권장)
//bad components/ |- TodoList.vue |- TodoItem.vue |- TodoButton.vue //good components/ |- SearchSidebar.vue |- SearchSidebarNavigation.vue
[구성 요소 이름은 상위 수준(일반적으로 일반적인 설명) 단어로 시작하고 설명 수정자로 끝나야 합니다.](강력 권장) 권장)The
前缀命名,以示其唯一性】(强烈推荐)
这不意味着组件只可用于一个单页面,而是每个页面只使用一次,这些组件永远不接受任何 prop
//bad components/ |- ClearSearchButton.vue |- ExcludeFromSearchInput.vue |- LaunchOnStartupCheckbox.vue |- RunSearchButton.vue |- SearchInput.vue |- TermsCheckbox.vue //good components/ |- SearchButtonClear.vue |- SearchButtonRun.vue |- SearchInputQuery.vue |- SearchInputExcludeGlob.vue |- SettingsCheckboxTerms.vue |- SettingsCheckboxLaunchOnStartup.vue
【和父组件紧密耦合的子组件应该以父组件名作为前缀命名】(强烈推荐)
//bad <!-- 在单文件组件和字符串模板中 --> <mycomponent/> <myComponent/> <!-- 在 DOM 模板中 --> <MyComponent></MyComponent> //good <!-- 在单文件组件和字符串模板中 --> <MyComponent/> <!-- 在 DOM 模板中 --> <my-component></my-component>
【组件名应该以高级别的 (通常是一般化描述的) 单词开头,以描述性的修饰词结尾】(强烈推荐)
//bad components/ |- SdSettings.vue |- UProfOpts.vue //good components/ |- StudentDashboardSettings.vue |- UserProfileOptions.vue
【单文件组件和字符串模板中组件名应总是PascalCase——但在DOM模板中总是kebab-case】(强烈推荐)
//bad <!-- 在单文件组件、字符串模板和 JSX 中 --> <MyComponent></MyComponent> <!-- 在 DOM 模板中 --> <my-component/> //good <!-- 在单文件组件、字符串模板和 JSX 中 --> <MyComponent/> <!-- 在 DOM 模板中 --> <my-component></my-component>
【组件名应该倾向于完整单词而不是缩写】(强烈推荐)
//bad <template><button class="btn btn-close">X</button></template> <style> .btn-close {background-color: red;} </style> //good <template><button class="btn btn-close">X</button></template> <style scoped> .btn-close {background-color: red;} </style> //good <template><button :class="[$style.button, $style.buttonClose]">X</button></template> <style module> .btn-close {background-color: red;} </style>
组件相关
【单文件组件、字符串模板和JSX中没有内容的组件应该自闭合——但在DOM模板里不要这样做】(强烈推荐)
自闭合组件表示它们不仅没有内容,而且刻意没有内容
//good <!-- ComponentA.vue --> <script>/* ... */</script> <template>...</template> <style>/* ... */</style> <!-- ComponentB.vue --> <script>/* ... */</script> <template>...</template> <style>/* ... */</style>
【为组件样式设置作用域】(必要)
这条规则只和单文件组件有关。不一定要使用 scoped
//bad Vue.component('TodoList', {}) Vue.component('TodoItem', {}) //good components/ |- TodoList.vue |- TodoItem.vue[구성 요소 이름 단일 파일 구성 요소 및 문자열 템플릿에서는 항상 PascalCase여야 하지만 DOM 템플릿에서는 항상 kebab-case여야 합니다.](적극 권장)
el[구성 요소 이름은 약어 대신 전체 단어로 표시되는 경향이 있습니다.](적극 권장)
name parentComponent 관련[JSX에서 단일 파일 구성 요소, 문자열 템플릿 및 내용이 없는 구성 요소는 자체적으로 닫혀야 합니다. 하지만 DOM 템플릿에서는 이 작업을 수행하지 마세요.] (강력히 권장됨) 자체 닫는 구성 요소는 내용이 없을 뿐만 아니라 , 그러나 의도적으로 내용이 없습니다
functional[구성요소 스타일 범위 설정](필수)이 규칙은 단일 파일 구성요소에만 관련됩니다.
scoped
속성을 사용하는 것은 필요하지 않습니다. 범위 설정은 CSS 모듈을 사용하거나 다른 라이브러리 또는 규칙을 사용하여 수행할 수도 있습니다. delimiters comments[단일 파일 구성 요소는 항상 3f1c4e4b6b16bbbd69b2ee476dc4f83a, d477f9ce7bf77f53fbcf36bec1b69b7a 및 c9ccee2e6ea535a969eb3f532ad9fe89 )
components directives filters【하나의 파일에 하나의 컴포넌트만】(강력히 권장)
extends mixins【컴포넌트 옵션의 기본 순서】(권장)1. 부작용(컴포넌트 외부에서 발생하는 효과)
inheritAttrs model props/propsData2. 컴포넌트 이외의 컴포넌트 필요)
data computed3. 컴포넌트 유형(컴포넌트 유형 변경)
watch 生命周期钩子 (按照它们被调用的顺序)4. 템플릿 수정자(템플릿 컴파일 방식 변경)
methods5. 템플릿)
template/render renderError6. 조합(속성을 옵션에 병합)
//bad props: ['status'] //good props: { status: String } //better props: { status: { type: String, required: true } }7. 인터페이스(구성 요소의 인터페이스)
//bad props: {'greeting-text': String} <WelcomeMessage greetingText="hi"/> //good props: {greetingText: String} <WelcomeMessage greeting-text="hi"/>8. 로컬 상태(로컬 반응형 속성)
//bad <li v-for="todo in todos"> //good <li v-for="todo in todos":key="todo.id">9.
//bad <li v-for="user in users" v-if="user.isActive" :key="user.id" > {{ user.name }} <li> //good <li v-for="user in users" v-if="shouldShowUsers" :key="user.id" > {{ user.name }} <li>10. 비반응형 속성(반응형 시스템에 의존하지 않는 인스턴스 속성)
//bad <img src="https://vuejs.org/images/logo.png"> //good <img src="https://vuejs.org/images/logo.png" >11. 렌더링(컴포넌트 출력에 대한 선언적 설명)
isprop[Prop 정의는 최대한 상세해야 합니다.] (필수)상세 prop 정의에는 두 가지 이점이 있습니다. 1. 컴포넌트의 API를 설명하므로 컴포넌트의 사용법을 쉽게 이해할 수 있습니다. 2. 개발 환경에서 잘못된 형식의 prop이 제공되는 경우; Vue는 잠재적인 오류 원인을 파악하는 데 도움이 되도록 경고합니다
v-for【props를 선언할 때 이름은 항상 camelCase를 사용해야 하며 템플릿과 JSX에서는 항상 kebab-case를 사용해야 합니다】(강력 추천)
v-if v-else-if v-else v-show v-cloak지시문 및 기능【v-for와 함께 전체 사용 키】(필수)
v-pre v-once【동일한 요소에 v-if와 v-for를 동시에 사용하지 마세요】(필수)
id【여러 요소가 있는 요소 특성은 여러 줄로 작성해야 합니다.] (강력히 권장)
ref key slot[요소 특성의 기본 순서] (권장) 1. 정의(구성 요소에 대한 옵션 제공)
v-model2. 동일한 요소의 여러 변형)
v-on3. 조건부 렌더링(요소가 렌더링/표시되는지 여부)
v-html v-text4. 렌더링 방법(요소의 렌더링 방법 변경)
//bad methods: {update: function () { }} //bad methods: {_update: function () { } } //bad methods: {$update: function () { }} //bad methods: {$_update: function () { }} //good methods: { $_myGreatMixin_update: function () { }}5. Component)
//bad Vue.component('some-comp', { data: { foo: 'bar' } }) //good Vue.component('some-comp', { data: function () { return { foo: 'bar' } } })6. 고유 기능(고유 값 특성 필수)
//bad {{ fullName.split(' ').map(function (word) { return word[0].toUpperCase() + word.slice(1) }).join(' ') }} //good computed: { normalizedFullName: function () { return this.fullName.split(' ').map(function (word) { return word[0].toUpperCase() + word.slice(1) }).join(' ') } }7. 양방향 바인딩(바인딩과 이벤트 결합)
//bad computed: { price: function () { var basePrice = this.manufactureCost / (1 - this.profitMargin) return ( basePrice - basePrice * (this.discountPercent || 0) ) } } //good computed: { basePrice: function () { return this.manufactureCost / (1 - this.profitMargin) }, discount: function () { return this.basePrice * (this.discountPercent || 0) }, finalPrice: function () { return this.basePrice - this.discount } }8. 기타 특성(모든 일반 바운드 또는 언바운드 특성)🎜🎜9. 이벤트(구성 요소 이벤트 리스너)🎜
//good props: { value: { type: String, required: true }, focused: { type: Boolean, default: false } }🎜10. 콘텐츠(요소의 콘텐츠 복사)🎜
//bad <style scoped> button { background-color: red; } </style> //good <style scoped> .btn-close { background-color: red; } </style>🎜Attributes🎜🎜[개인 속성 이름](필수)🎜🎜플러그인에서 사용자 정의된 개인 속성에는 항상 $_ 접두사를 사용하세요. , 믹스인 및 기타 확장 기능이 포함되어 있습니다. 그리고 다른 작성자와의 충돌을 피하기 위한 네임스페이스가 함께 제공됩니다(예: $_yourPluginName_)🎜
//bad <p v-if="error"> 错误:{{ error }} </p> <p v-else> {{ results }} </p> //good <p v-if="error" key="search-status" > 错误:{{ error }} </p> <p v-else key="search-results" > {{ results }} </p>🎜[구성 요소의 데이터는 함수여야 합니다](필수)🎜
当在组件中使用 data 属性的时候 (除了 new Vue 外的任何地方),它的值必须是返回一个对象的函数
//bad Vue.component('some-comp', { data: { foo: 'bar' } }) //good Vue.component('some-comp', { data: function () { return { foo: 'bar' } } })
【组件模板应该只包含简单的表达式,复杂的表达式则应该重构为计算属性或方法】(强烈推荐)
//bad {{ fullName.split(' ').map(function (word) { return word[0].toUpperCase() + word.slice(1) }).join(' ') }} //good computed: { normalizedFullName: function () { return this.fullName.split(' ').map(function (word) { return word[0].toUpperCase() + word.slice(1) }).join(' ') } }
【应该把复杂计算属性分割为尽可能多的更简单的属性】(强烈推荐)
//bad computed: { price: function () { var basePrice = this.manufactureCost / (1 - this.profitMargin) return ( basePrice - basePrice * (this.discountPercent || 0) ) } } //good computed: { basePrice: function () { return this.manufactureCost / (1 - this.profitMargin) }, discount: function () { return this.basePrice * (this.discountPercent || 0) }, finalPrice: function () { return this.basePrice - this.discount } }
【当组件开始觉得密集或难以阅读时,在多个属性之间添加空行可以让其变得容易】(推荐)
//good props: { value: { type: String, required: true }, focused: { type: Boolean, default: false } }
谨慎使用
1、元素选择器应该避免在 scoped 中出现
在 scoped
样式中,类选择器比元素选择器更好,因为大量使用元素选择器是很慢的
//bad <style scoped> button { background-color: red; } </style> //good <style scoped> .btn-close { background-color: red; } </style>
2、应该优先通过 prop 和事件进行父子组件之间的通信,而不是 this.$parent
或改变 prop
3、应该优先通过 Vuex 管理全局状态,而不是通过 this.$root
或一个全局事件总线
4、如果一组 v-if
+ v-else
的元素类型相同,最好使用 key
(比如两个 e388a4556c0f65e1904146cc1a846bee
元素)
//bad <p v-if="error"> 错误:{{ error }} </p> <p v-else> {{ results }} </p> //good <p v-if="error" key="search-status" > 错误:{{ error }} </p> <p v-else key="search-results" > {{ results }} </p>
上面是我整理给大家的,希望今后会对大家有帮助。
相关文章:
위 내용은 Vue에서 간소화된 스타일을 구현하는 방법(자세한 튜토리얼)의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!