#Vue.js 3 Guide: Composition API, Components, and State Management
Vue.js is a progressive JavaScript framework for building user interfaces. Vue 3 introduces the Composition API, improved reactivity, and better TypeScript support.
#Installation and Setup
#CDN
<script src="https://unpkg.com/vue@3/dist/vue.global.js"></script>
#Vite (Recommended)
npm create vue@latest my-vue-app
cd my-vue-app
npm install
npm run dev
#Creating a Vue App
import { createApp } from 'vue';
import App from './App.vue';
createApp(App).mount('#app');
#Template Syntax
#Text Interpolation
<span>{{ message }}</span>
#Raw HTML
<p v-html="rawHtml"></p>
#Attribute Binding
<div v-bind:id="dynamicId"></div>
<!-- shorthand -->
<div :id="dynamicId"></div>
#JavaScript Expressions
{{ number + 1 }} {{ ok ? 'YES' : 'NO' }}
#Reactivity with ref and reactive
#ref for Primitive Values
<script setup>
import { ref } from 'vue';
const count = ref(0);
function increment() {
count.value++;
}
</script>
<template>
<button @click="increment">{{ count }}</button>
</template>
#reactive for Objects
<script setup>
import { reactive } from 'vue';
const state = reactive({ count: 0 });
</script>
<template>
<button @click="state.count++">{{ state.count }}</button>
</template>
#Components
#Defining a Component
<!-- ChildComponent.vue -->
<template>
<div>
<h3>{{ title }}</h3>
<slot></slot>
</div>
</template>
<script setup>
defineProps(['title']);
</script>
#Using a Component
<template>
<ChildComponent title="Hello">
<p>This is slotted content</p>
</ChildComponent>
</template>
<script setup>
import ChildComponent from './ChildComponent.vue';
</script>
#Props and Events
#Props
<script setup>
defineProps({
name: String,
age: {
type: Number,
default: 18,
},
});
</script>
#Emitting Events
<script setup>
const emit = defineEmits(['update']);
function sendUpdate() {
emit('update', 'new value');
}
</script>
#Composition API: Lifecycle Hooks
<script setup>
import { onMounted, onUnmounted } from 'vue';
onMounted(() => {
console.log('Component mounted');
});
onUnmounted(() => {
console.log('Component unmounted');
});
</script>
#Computed Properties
<script setup>
import { ref, computed } from 'vue';
const firstName = ref('John');
const lastName = ref('Doe');
const fullName = computed(() => `${firstName.value} ${lastName.value}`);
</script>
<template>
<p>{{ fullName }}</p>
</template>
#Watchers
<script setup>
import { ref, watch } from 'vue';
const count = ref(0);
watch(count, (newVal, oldVal) => {
console.log(`Count changed from ${oldVal} to ${newVal}`);
});
</script>
#Routing with Vue Router
#Installation
npm install vue-router@4
#Setup
// router/index.js
import { createRouter, createWebHistory } from 'vue-router';
import Home from '../views/Home.vue';
const routes = [
{ path: '/', component: Home },
{ path: '/about', component: () => import('../views/About.vue') },
];
const router = createRouter({
history: createWebHistory(),
routes,
});
export default router;
#Using in App
import { createApp } from 'vue';
import App from './App.vue';
import router from './router';
createApp(App).use(router).mount('#app');
#Navigation
<template>
<router-link to="/">Home</router-link>
<router-link to="/about">About</router-link>
<router-view></router-view>
</template>
#State Management with Pinia (Vue 3)
#Installation
npm install pinia
#Creating a Store
// stores/counter.js
import { defineStore } from 'pinia';
export const useCounterStore = defineStore('counter', {
state: () => ({ count: 0 }),
actions: {
increment() {
this.count++;
},
},
getters: {
doubleCount: (state) => state.count * 2,
},
});
#Using the Store
<script setup>
import { useCounterStore } from '@/stores/counter';
const counter = useCounterStore();
</script>
<template>
<p>{{ counter.count }}</p>
<p>Double: {{ counter.doubleCount }}</p>
<button @click="counter.increment()">+1</button>
</template>
#Best Practices
- Use Composition API with
<script setup>for better organization. - Keep components small and focused.
- Leverage TypeScript for type safety.
- Use Pinia for global state instead of Vuex (Pinia is the official state management for Vue 3).
- Follow Vue Style Guide for consistent code.