国产成人精品18p,天天干成人网,无码专区狠狠躁天天躁,美女脱精光隐私扒开免费观看

vue單文件組件的實(shí)現

發(fā)布時(shí)間:2021-08-17 12:16 來(lái)源: 閱讀:0 作者:諸葛韓信 欄目: JavaScript 歡迎投稿:712375056

最近翻閱了一下vue。發(fā)覺(jué)有一個(gè)單文件組件之前基本忽視掉了。vue.js中的單文件組件允許在一個(gè)文件中定義一個(gè)組件的所有內容。也就是說(shuō),一個(gè)頁(yè)面或者是一個(gè)組件,我們想將他們捆綁在一起,那么vue的這個(gè)單文件組件可以做到。正如vue的官網(wǎng)說(shuō)的,“在很多 Vue 項目中,我們使用 app.component 來(lái)定義全局組件,緊接著(zhù)用 app.mount('#app') 在每個(gè)頁(yè)面內指定一個(gè)容器元素?!边@里的組件,都是相對簡(jiǎn)單的,而面對一個(gè)比較復雜的項目,這種方式就行不通。原因如下:

  • 全局定義 (Global definitions) 強制要求每個(gè) component 中的命名不得重復;
  • 字符串模板 (String templates) 缺乏語(yǔ)法高亮,在 HTML 有多行的時(shí)候,需要用到丑陋的 \;
  • 不支持 CSS (No CSS support) 意味著(zhù)當 HTML 和 JavaScript 組件化時(shí),CSS 明顯被遺漏;
  • 沒(méi)有構建步驟 (No build step) 限制只能使用 HTML 和 ES5 JavaScript,而不能使用預處理器,如 Pug
  • (曾經(jīng)的 Jade) 和 Babel。

所有這些都可以通過(guò)擴展名為 .vue 的 single-file components (單文件組件) 來(lái)解決,并且還可以使用 webpack 或 Browserify 等構建工具。
那么vue項目中的單文件組件需要如何創(chuàng )建呢?

構建

npm install -D @vue/compiler-sfc

在控制臺上輸入上述的代碼,然后就會(huì )出現一個(gè)文件夾和另一個(gè)json文件。如下:


我們要構建單文件組件,就要自個(gè)制定文件。同時(shí)對webpack也要有一定的了解才行。
比如說(shuō),我們自己安裝一些需要的依賴(lài)。比如說(shuō),css-loader、css的預編譯處理器等等。因為需要項目對vue文件進(jìn)行解析,那么vue-loader是必須的。

這些文件其實(shí)都是vue的簡(jiǎn)單版本。比如簡(jiǎn)單版的hello.vue文件,可以如下


由此可以看見(jiàn): 三個(gè)部分組成。而template這個(gè)部分是不可缺少的,其它的兩個(gè)部分,style和script還可以忽略掉。
script讓你的頁(yè)面js可以跟vue完美結合,而style可以使用預處理器來(lái)構建簡(jiǎn)潔和功能更豐富的組件。(這個(gè)單文件組件很像最初前端開(kāi)發(fā)中的html文檔,它有自己的style標簽和script標簽,只是表現層使用一個(gè)template標簽。由于使用了簡(jiǎn)單的方式,得到一個(gè)強大的分層組件(內容/模板:,表現:


可能有的小伙伴喜歡將不同模塊拆分開(kāi)來(lái),也就是vue文檔說(shuō)的關(guān)注點(diǎn)分離。那么沒(méi)有關(guān)系,你可以拆開(kāi)那些文檔,將css和js拆開(kāi)到另一個(gè)文件,之后引入進(jìn)組件中。如下:

<!-- my-component.vue -->
<template>
  <div>This will be pre-compiled</div>
</template>
<script src="./my-component.js"></script>
<style src="./my-component.css"></style>

項目大致目錄如下:

其中,index.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <title>Vue Simple Todo App with SFC</title>
    <link
      rel="stylesheet"
      href="https://cdnjs.cloudflare.com/ajax/libs/normalize/8.0.1/normalize.min.css" rel="external nofollow"  rel="external nofollow" 
    />
    <link rel="stylesheet" href="/dist/main.css" rel="external nofollow"  rel="external nofollow"  />
  </head>
  <body>
    <div id="app"></div>
    <script src="/dist/main.js"></script>
  </body>
</html>

package.json

{
    "private": true,
    "scripts": {
      "dev": "webpack-dev-server",
      "build": "webpack --env.prod"
    },
    "dependencies": {
      "vue": "^3.1.1"
    },
    "devDependencies": {
      "@vue/compiler-sfc": "^3.1.1",
      "css-loader": "^3.5.2",
      "file-loader": "^6.0.0",
      "mini-css-extract-plugin": "^0.9.0",
      "stylus": "^0.54.7",
      "stylus-loader": "^3.0.2",
      "url-loader": "^4.1.0",
      "vue-loader": "^16.0.0-alpha.3",
      "vue-style-loader": "^4.1.2",
      "webpack": "^4.42.1",
      "webpack-cli": "^3.3.11",
      "webpack-dev-server": "^3.10.3"
    },
    "keywords": ["todo", "vue"],
    "name": "vue-todo-list-app-with-single-file-component",
    "description": "A simple todo list application written in Vue with Single File Component (SFC) support."
  }

webpack.config.js

const path = require("path");
const { VueLoaderPlugin } = require("vue-loader");
const MiniCssExtractPlugin = require("mini-css-extract-plugin");

module.exports = (env = {}) => ({
  mode: env.prod ? "production" : "development",
  devtool: env.prod ? "source-map" : "cheap-module-eval-source-map",
  entry: [
    env.prod ? false : require.resolve(`webpack-dev-server/client`),
    path.resolve(__dirname, "./src/main.js")
  ].filter(Boolean),
  output: {
    path: path.resolve(__dirname, "./dist"),
    publicPath: "/dist/"
  },
  resolve: {
    alias: {
      // this isn't technically needed, since the default `vue` entry for bundlers
      // is a simple `export * from '@vue/runtime-dom`. However having this
      // extra re-export somehow causes webpack to always invalidate the module
      // on the first HMR update and causes the page to reload.
      vue: "@vue/runtime-dom"
    }
  },
  module: {
    rules: [
      {
        test: /\.vue$/,
        use: "vue-loader"
      },
      {
        test: /\.png$/,
        use: {
          loader: "url-loader",
          options: { limit: 8192 }
        }
      },
      {
        test: /\.css$/,
        use: [
          {
            loader: MiniCssExtractPlugin.loader,
            options: { hmr: !env.prod }
          },
          "css-loader"
        ]
      },
      {
        test: /\.stylus$/,
        use: ["vue-style-loader", "css-loader", "stylus-loader"]
      },
      {
        test: /\.pug$/,
        loader: "pug-plain-loader"
      }
    ]
  },
  plugins: [
    new VueLoaderPlugin(),
    new MiniCssExtractPlugin({
      filename: "[name].css"
    })
  ],
  devServer: {
    inline: true,
    hot: true,
    stats: "minimal",
    contentBase: __dirname,
    overlay: true,
    injectClient: false,
    disableHostCheck: true
  }
});

test.html

<!DOCTYPE html>
<html lang="en">
  <head>
    <meta charset="utf-8" />
    <title>Vue Simple Todo App with SFC</title>
    <link
      rel="stylesheet"
       rel="external nofollow"  rel="external nofollow" 
    />
    <link rel="stylesheet" href="/dist/main.css" rel="external nofollow"  rel="external nofollow"  />
  </head>
  <body>
    <div id="app222">test pages</div>
    <script src="/dist/main.js"></script>
  </body>
</html>

src文件夾里邊有三個(gè)文件,App.vue main.js 和TodoItem.vue

其中:App.vue

<template>
  <div class="wrapper">
    <h1>My Todo List</h1>
    <form @submit.prevent="addTodo">
      <input type="text" name="todo-text" v-model="newTodoText" placeholder="New todo">
    </form>
    <ul v-if="todos.length">
      <TodoItem v-for="todo in todos" :key="todo.id" :todo="todo" @remove="removeTodo"/>
    </ul>
    <p class="none" v-else>Nothing left in the list. Add a new todo in the input above.</p>
  </div>
</template>

<script>
import TodoItem from "./TodoItem.vue"

let nextTodoId = 1

const createTodo = text => ({
  text,
  id: nextTodoId++
})

export default {
  components: {
    TodoItem
  },

  data() {
    return {
      todos: [
        createTodo("Learn Vue"),
        createTodo("Learn about single-file components"),
        createTodo("Fall in love ❤️")
      ],

      newTodoText: ""
    }
  },

  methods: {
    addTodo() {
      const trimmedText = this.newTodoText.trim()

      if (trimmedText) {
        this.todos.push(createTodo(trimmedText))
      }

      this.newTodoText = ""
    },

    removeTodo(item) {
      this.todos = this.todos.filter(todo => todo !== item)
    }
  }
}
</script>

<style lang="stylus">
*, *::before, *::after 
  box-sizing border-box

html, body
  font 16px/1.2 BlinkMacSystemFont, -apple-system, "Segoe UI", Roboto, Helvetica, Arial, sans-serif
  padding 10px

.wrapper
  width 75%
  margin 0 auto

form
  margin-bottom 20px

input[type="text"]
  width 100%
  padding 10px
  border 1px solid #777

ul, li
  margin 0
  padding 0

p.none
  color #888
  font-size small
</style>

main.js

import { createApp } from 'vue'
import App from './App.vue'

createApp(App).mount('#app')

TodoItem.vue

<template>
  <li>
    <span>{{ todo.text }}</span>
    <button @click.prevent="$emit('remove', todo)">Remove</button>
  </li>
</template>

<script>
export default {
  props: {
    todo: {
      required: true,
      type: Object
    }
  }
}
</script>


<style lang="stylus" scoped>
li
  display flex
  margin 5px 0

  span
    flex 1
  
  button
    border 1px solid orange
    background orange 
    color white
    font-size 0.8rem
    padding 2px 4px
    cursor pointer

    &:hover
      border-color #ff8100
      background #ff8100
</style>

注意
如果不懂得webpack,建議還是按照官網(wǎng)的指示,用vue的腳手架安裝基本的工具。
或者是按照我給的pakage.json放到項目上,npm install一下,安裝好最基本的環(huán)境,然后可以通過(guò)npm run dev進(jìn)行本地開(kāi)發(fā)。

其實(shí),我覺(jué)得這個(gè)單文件組件用處已經(jīng)比較小。除非就是一個(gè)純js的項目,用的庫和組件都已經(jīng)非常的古老,那么這個(gè)時(shí)候用這個(gè)單文件組件來(lái)進(jìn)行新的功能開(kāi)發(fā),效果還是不錯的,前提是你要對vue比較熟悉。同時(shí),我建議還是要學(xué)習一下webpack。不要對bable都一竅不通,然后還要通過(guò)node去啟動(dòng)項目。

其實(shí),用一個(gè)文件就將html/css/JavaScript分層管理,統一到了一個(gè)文件,著(zhù)實(shí)能夠讓我們的項目看起來(lái)更加的有條理,規范性更加好。因為我們的jq時(shí)代,常常會(huì )將css混雜在html中,而且,簡(jiǎn)單的一個(gè)點(diǎn)擊事件都要將它們分割開(kāi),這體驗當然沒(méi)有“分層而治”那么分明。

參考文獻:
1、
2、

到此這篇關(guān)于vue單文件組件的實(shí)現的文章就介紹到這了,更多相關(guān)vue單文件組件內容請搜索腳本之家以前的文章或繼續瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

免責聲明:本站發(fā)布的內容(圖片、視頻和文字)以原創(chuàng )、來(lái)自本網(wǎng)站內容采集于網(wǎng)絡(luò )互聯(lián)網(wǎng)轉載等其它媒體和分享為主,內容觀(guān)點(diǎn)不代表本網(wǎng)站立場(chǎng),如侵犯了原作者的版權,請告知一經(jīng)查實(shí),將立刻刪除涉嫌侵權內容,聯(lián)系我們QQ:712375056,同時(shí)歡迎投稿傳遞力量。

在线天堂新版资源www在线| 人妻无码中文字幕免费视频蜜桃| 国产精品国产亚洲精品看不卡| 丁香花免费高清视频完整版| 一夲道DVD高清无码| 亚洲日韩中文字幕在线不卡最新|