Skip to content

Blog Công Nghệ

MENUMENU
  • Trang chủ
  • Giới Thiệu
  • Lập Trình
    • Lập Trình Website
      • Laravel
        • Phân Tích Dự Án
      • PHP
      • SQL
      • HTML
      • CSS
      • Javascipt
      • My Project
      • Wordpress
    • Luyện Skill
    • Lập trình winform
    • CSDL
    • Lập Trình Android
    • Trí tuệ nhân tạo
    • Khai Khoáng Dữ Liệu
    • Arduino
    • Khác
    • Đồ án
  • Phần Mềm
    • Powerpoint
    • Tool
  • Cuộc sống và Giải trí
    • Hợp âm
    • web5ngay - youtube
    • Công Giáo
    • Kỹ Năng Sống
    • Street Workout
  • Danh sách bài viết
  • Guide line
    • Guild line phỏng vấn
    • Guide lines Laravel
    • Guide line Module Frontend
  • Tóm tắt sách
  • Fanpage

Blog Công Nghệ

Nơi chia sẻ kiến thức

Kinh nghiệm VueJS

1 Tháng Hai, 2023 by admin
Lượt xem: 122

 

Contents

  • 1. Điểm tương đồng giữa React và VueJS
  • 2. Những kiến thức chung
    • 2.1 Vue Router
      • 2.1.1 Cài đặt
      • 2.1.2 import
      • 2.1.3 Link to ở component
      • 2.1.4 Redirect
      • 2.1.5 get param
      • 2.1.6 Sử dụng html thay vì component
      • 2.1.7 Go back route
    • 2.2 VueX
      • 2.2.1 Cài đặt
      • 2.2.2 Tạo store
      • 2.2.3 Gắn Store vào main.js
      • 2.2.4 Tạo modules
        • FILE MODULES MẪU
      • 2.2.5 Sử dụng ở Component
    • 2.3 Form validate
  • 3. Kinh nghiệm
    • 3.1 Cài vue cli
    • 3.2 Cài project Vue
    • 3.3 Lệnh run server
    • 3.4 Build deploy server
    • 3.5 Props
      • 3.5.1 Truyền method
    • 3.6 Sử dụng sass/scss trong vue
    • 3.6 Yêu cầu vue re render DOM
    • 3.7 Console trong template
    • 3.8 Sử dụng mixin để tối ưu code
    • 3.9 Thư viện hỗ trợ vuejs
      • 3.9.1 Thanh scroll dạng mảnh
    • 3.10 Các khái niệm học thêm được
    • 3.11 Sử dụng vuejs vào file html
    • 3.12 Watch trong vuejs phải có trong data
    • 3.13 Radar chart vuejs – chartjs
    • 3.14 Sử dụng biến trong file .env

1. Điểm tương đồng giữa React và VueJS

Vue React
Data State
VueX Redux
Vue Router Router
Component Components
Props Props
npm npm

2. Những kiến thức chung

Cấu trúc thư mục:

+src:

+main.js

+App.vue => component gốc

+assets: hình ảnh, font

+components

+component

+Template : nội dung phải nằm chung 1 thẻ bao đóng

+Script

+Style: hỗ trợ cả css và scss

      • scoped style: style dành riêng cho component

+Tạo component:

+Tạo file .vue

+Import vào component cha

+Khai báo vào component cha

+ 2 ways binding:

+Life cycle:

+Binding:

+Value Binding:  {{ tenBien }}

+Property Binding: 

v-bind:id="tenBien"
//viết tắt
:id="tenBien"

+style and class binding:

:class="tenBien"
/*
	Tên biến:
    + Kiểu dữ liệu: bool
    + Nếu true thì gắn tên class vào component
    + else thì không
*/

+Model: Liên kết 1 element với 1 property

V-model

+Even Handling:

v-on:click="tenHam()"
//viết tắt:
@click="TenHam()"

+prevent default event: Hủy event mặc định

@click.prevent

+ ref: Ánh xạ chỉnh element

this.$refs.tenRef

+ condition rendering

v-show
v-hide
v-if
v-else-if
v-else

+list rendering

v-for="(tenBienTam, index) in mang" :key="index"

+methods: hàm của vue object

methods: {
  addTasks: function() {
    //biến sử dụng this.tenBien
  }
}

+watch: theo dõi sự thay đổi của Data

watch: {
 	tenBien: function() {
      //code
    },
  	tenBien: function(newValue, oldValue) {
      //code
    }
}

+hooks: Như trong life cycle

mounted() {
  
}
....

+props: truyền dữ liệu component cha và component con

props: [
  'tenProps'
]

//component cha
:tenProps="tenBien"

+filter:

ví dụ: 100000 => 100,000

Property vẫn là 100000 để có thể tính toán tiếp còn html render sẽ là 100,000

filters: {
  	abc: function() {
      //code
    }
}

//chỗ fileter
{{ tenBien | abc }}

Video mình học:

2.1 Vue Router

2.1.1 Cài đặt

2.1.2 import

import VueRouter from 'vue-router'
  
Vue.use(VueRouter);

const routes = [
  { 
    name: 'Login',
    path: '/login',
    component: Login
  },
  { 
    name: 'CreateEvent',
    path: '/create-event',
    component: CreateEvent,
    //beforeEach: checkRoute
  },
  { 
    name: 'Calendar',
    path: '/',
    component: Calendar,
    //beforeEach: checkRoute
  },
  { 
    name: 'CreateTask',
    path: '/create-task',
    component: CreateTask,
    //beforeEach: checkRoute
  },
  { 
    name: 'EditEvent',
    path: '/edit-event/:id',
    component: EditEvent,
    //beforeEach: checkRoute
  },
]

const router = new VueRouter({
  routes, // short for `routes: routes`
  mode: 'history'
})

router.beforeEach( (to, from, next) => {
  /**
   * if route là /login => allow
   */
  if (to.fullPath == "/login"){
    return next();
  }

  /**
   * if localStorage.getItem("username") has data
   *    => allow access
   * else equals "" || undefine || not exists => (not data)
   *    => not allow
   *    => redirect login page
   */
  if ( localStorage.getItem("username") ) {
    return next();
  } else {
    console.log("else next");
    return next({ path: '/login'}); 
  }
});

new Vue({
  router,
  store,
  render: h => h(App)
}).$mount('#app')

2.1.3 Link to ở component

<router-link :to="'/create-event/' + this.dateSelect + '/abcUser'">
  <ButtonCreate />
</router-link>

2.1.4 Redirect

this.$router.push({ path: '/' });

//or
this.$router.push({ name: 'Calendar' });

//or
this.$router.push({ name: 'EditEvent', params: { id: id }});

2.1.5 get param

date: this.$route.params.date,
userName: this.$route.params.user

2.1.6 Sử dụng html thay vì component

const routes = [
    {
        path: '*',
        name: '404',
        component: {
          template: '<div>Not Found</div>'
        }
    }
  ];

2.1.7 Go back route

$router.go(-1)

2.2 VueX

2.2.1 Cài đặt

npm install vuex

2.2.2 Tạo store

Tạo:

  • folder src/store
  • file store/index.js
//file index.js
import Vuex from 'vuex';
import Vue from 'vue';
import todos from './modules/todos';

// Load Vuex
Vue.use(Vuex);

// Create store
export default new Vuex.Store({
  modules: {
    todos
  }
});

2.2.3 Gắn Store vào main.js

import Vue from 'vue'
import App from './App.vue'
import store from './store';

Vue.config.productionTip = false

new Vue({
  store,
  render: h => h(App),
}).$mount('#app')

2.2.4 Tạo modules

Tạo:

  • folder store/mudules
  • file modules/tenFile.js

Ở đây mình lấy ví dụ todo.js

//file todo.js
import axios from 'axios';

const state = {
  
};

const getters = {
 
};

const actions = {
  
};

const mutations = {
  
};

export default {
  state,
  getters,
  actions,
  mutations
};
  • state: nơi chứa state, data
  • getters: cho các component lấy dữ liệu
  • actions: cho các component set dữ liệu
  • mutations: nơi set lại state, data từ action
FILE MODULES MẪU
import axios from 'axios';

const state = {
  todos: []
};

const getters = {
  allTodos: state => state.todos
};

const actions = {
  async fetchTodos({ commit }) {
    const response = await axios.get(
      'https://jsonplaceholder.typicode.com/todos'
    );

    commit('setTodos', response.data);
  },
  async addTodo({ commit }, title) {
    const response = await axios.post(
      'https://jsonplaceholder.typicode.com/todos',
      { title, completed: false }
    );

    commit('newTodo', response.data);
  },
  async deleteTodo({ commit }, id) {
    await axios.delete(`https://jsonplaceholder.typicode.com/todos/${id}`);

    commit('removeTodo', id);
  },
  async filterTodos({ commit }, e) {
    // Get selected number
    const limit = parseInt(
      e.target.options[e.target.options.selectedIndex].innerText
    );

    const response = await axios.get(
      `https://jsonplaceholder.typicode.com/todos?_limit=${limit}`
    );

    commit('setTodos', response.data);
  },
  async updateTodo({ commit }, updTodo) {
    const response = await axios.put(
      `https://jsonplaceholder.typicode.com/todos/${updTodo.id}`,
      updTodo
    );

    console.log(response.data);

    commit('updateTodo', response.data);
  }
};

const mutations = {
  setTodos: (state, todos) => (state.todos = todos),
  newTodo: (state, todo) => state.todos.unshift(todo),
  removeTodo: (state, id) =>
    (state.todos = state.todos.filter(todo => todo.id !== id)),
  updateTodo: (state, updTodo) => {
    const index = state.todos.findIndex(todo => todo.id === updTodo.id);
    if (index !== -1) {
      state.todos.splice(index, 1, updTodo);
    }
  }
};

export default {
  state,
  getters,
  actions,
  mutations
};

2.2.5 Sử dụng ở Component

import { mapGetters, mapActions } from "vuex";

export default {    
        name: 'ListTodo',
        components: { Todo },
        computed: mapGetters(["allTodos"]),
        methods: {
            ...mapActions(["fetchTodos"]),
            dbClickItemTodo(id) {
              
            }
        },
        created() {
            this.fetchTodos();
        }
    }
  • import vào
  • getter ở dòng 6: chứa các hàm định nghĩa ở modules
  • action ở dòng 8, chứa các hàm định nghĩa ở modules

2.3 Form validate

3. Kinh nghiệm

Cần setup:

  • Cài Nodejs
  • Vue CLI
  • Vue Project

3.1 Cài vue cli

npm install -global @vue/cli
//hoặc gọn hơn
npm i -g @vue/cli
  
  
//kiểm tra
vue --version

3.2 Cài project Vue

vue create tenProject
  chọn => Default([vue2],.....)

3.3 Lệnh run server

npm run serve

3.4 Build deploy server

npm run build

Khi chạy xong nó sẽ build ra thư mục dist. Từ thư mục này có thể up lên hosting.

3.5 Props

3.5.1 Truyền method

//Component cha
<template>
    <AddTodo :submitForm="addTodo"/>
</template>


<script>
import AddTodo from './components/todo/AddTodo';

export default {
  ...
  methods: {
    addTodo(todo) {
      this.TodoData = [...this.TodoData, {content: todo}];
    }
  }
}
</script>
<template>
...
</template>

<script>
    export default {
       ...
        props: {
            submitForm: { type: Function }
        },
        methods: {
            submit() {
                this.submitForm(this.inputText);
                this.inputText = "";
            }
        }

    }
</script>

3.6 Sử dụng sass/scss trong vue

Ban đầu chạy comment line tại thư mục gốc

npm install -D sass-loader node-sass

Sau đó trong thư mục gốc tạo file webpack.config.js và paste nội dung bên dưới vào.

{
  test: /\.sass$/,
  use: [
    'vue-style-loader',
    'css-loader',
    {
      loader: 'sass-loader',
      options: {
        indentedSyntax: true,
        // sass-loader version >= 8
        sassOptions: {
          indentedSyntax: true
        }
      }
    }
  ]
}

npm run server => để run lại server

3.6 Yêu cầu vue re render DOM

this.$forceUpdate();

3.7 Console trong template

<template>
{{ test() }}
</template>
  
  
<script>
  	method: {
     	test () {
         	console.log('abc'); 
        }
    }
</script>

3.8 Sử dụng mixin để tối ưu code

//mixin.js
export default {
   data () {
      title: 'Mixin'
   }
}
import mixin from './mixin.js'
export default {
   mixins: [mixin],
   
   data () {
      title: 'Component'
   },
   
   created: function () {
      console.log(this.title)
   }
}
// => "Component"

Xem thêm bài viết: https://viblo.asia/p/cach-su-dung-mixin-trong-vuejs-Qpmle7QrKrd

3.9 Thư viện hỗ trợ vuejs

  • Validate: V-mask        https://www.npmjs.com/package/v-mask

3.9.1 Thanh scroll dạng mảnh

Demo: https://lab.morioh.com/v-smooth-scrollbar/

npm i @morioh/v-smooth-scrollbar
import Vue from 'vue'
import ScrollBar from '@morioh/v-smooth-scrollbar'

// global register
Vue.use(ScrollBar);
<div v-scrollbar style="max-height: 500px; max-height:500px"></div>

3.10 Các khái niệm học thêm được

  1. Two-way binding: template thay đổi thì data thay đổi và ngược lại.
  2. refs: lấy dom để làm một việc gì đó giống document.getElementById…
  3. Emit custom event: tạo sự kiện component con lên component cha để thay đổi data của component cha.
    https://viblo.asia/p/giao-tiep-giua-cac-component-trong-vuejs-gDVK29yw5Lj
  4. provide/inject: làm cho việc truyền dữ liệu giữa component ông, cố, cụ kị xuống component con dễ hơn. không phỉa bị sót khi truyền thông qua props.
  5. diving deeper:
    + scope style: style chỉ áp dụng cho component.
    + slots: tạo khoảng trống component con để component cha có thể thêm content vào đó.
    + Compilation slots: sử dụng slots có biến
  6. Computed khác method: computed chỉ sử dụng data của component, không thể truyền tham số, lưu caching nên xử lý nhanh hơn.
  7. Plugin: Tạo ra mục đích giống như wordpress, import vào là xài bất cứ đâu, không xài nữa chỉ cần gỡ ra.
    https://viblo.asia/p/gioi-thieu-don-gian-ve-plugin-trong-vue-1VgZvVR2ZAw

3.11 Sử dụng vuejs vào file html

let param = {
    DOM_QueryToVueBinding: '#app'
}

let data = `
<script src="https://code.jquery.com/jquery-3.6.0.min.js" integrity="sha256-/xUj+3OJU5yExlq6GSYGSHk7tPXikynS7ogEvDej/m4=" crossorigin="anonymous"></script>
<script src="https://unpkg.com/vue/dist/vue.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/axios/0.21.1/axios.min.js" integrity="sha512-bZS47S7sPOxkjU/4Bt0zrhEtWx0y0CRkhEp8IckzK+ltifIIE9EMIMTuT/mEzoIMewUINruDBIR/jJnbguonqQ==" crossorigin="anonymous" referrerpolicy="no-referrer"></script>

<script>
		$(document).ready(function () {
			new Vue({
				el: 'DOM_QUERY',
				data() {
					return {

					}
				},
                mounted() {
				},
				methods: {
				},
				watchs: {
				},
			})
		});
</script>
`;

data = data.replaceAll('DOM_QUERY', param.DOM_QueryToVueBinding);

console.log(data);
console.log('Thêm class or id ở trên (el: ...) vào template');

3.12 Watch trong vuejs phải có trong data

Đừng để mất thời gian vì điều này, hãy nhớ có trong data mới watch được. Mình từng bị điều này mất cả ngày trời để mò mẫm.

// Muốn watch được thuộc tính c trong form
...
  watch: {
   	"form.c": function() {
      // code
    }
  }
...
  
// Muốn chạy được thì trong data
...
  data() {
  	return {
      form: {
        a: 1,
        b: '',
        c: ''
      }
    }
  }
...
  
// Thay vì như thế nào => sẽ không bao giờ watch được
...
  data() {
  	return {
      form: {
        a: 1,
        b: '',
      }
    }
  }

3.13 Radar chart vuejs – chartjs

https://www.chartjs.org/docs/2.9.4/

https://github.com/tronghao/module-frontend

Vue => Chart => Radar

<RadarChart :labels="chart.labels" :data="chart.data" />
  
chart: {
  labels: ['メンテンス性', 'PCスペック', 'ロマン', 'ケーブル整理', '作業領域', '収納力'],
  data: [4, 3, 5, 2, 4, 5],
},

3.14 Sử dụng biến trong file .env

Muốn sử dụng được thì biến phải có tiền tố MIX_ nếu build bằng webpack laravel.

// in .env
MIX_BASIC_AUTH_USERNAME
MIX_BASIC_AUTH_PASSWORD
  
// in vue
process.env.MIX_BASIC_AUTH_USERNAME
process.env.MIX_BASIC_AUTH_PASSWORD

Related posts:

  1. Kinh nghiệm npm – package
  2. Kinh nghiệm React
  3. Kinh nghiệm Codeigniter – Perfex CRM
  4. Kinh nghiệm PHP

Post navigation

Previous Post:

Kinh nghiệm Angular

Next Post:

Kinh nghiệm npm – package

Trả lời Hủy

Email của bạn sẽ không được hiển thị công khai. Các trường bắt buộc được đánh dấu *

Ẩn sidebar

Tìm kiếm

Generic selectors
Exact matches only
Search in title
Search in content
Search in posts
Search in pages

Blog Công Nghệ

Bài viết mới

  • Master typescript
  • Sendmail trong Laravel sử dụng dịch vụ SES, SQS của Amazon
  • Install SSL in Nginx Ubuntu
  • Docker study
  • Bảo vệ: Hướng dẫn code bot Telegram easy game

Lượng truy cập

0074729
Visit Today : 325
Visit Yesterday : 178
This Month : 1000
Who's Online : 2
© 2025 Blog Công Nghệ | WordPress Theme by Superbthemes