Template Syntax and Data Rendering
Bind data to the DOM using mustache syntax or directives.
<div id="root">
<p>{{ greeting }}</p>
<span v-text="rawText"></span>
<div v-html="htmlContent"></div>
<input v-model="formInput" placeholder="Type here">
<a v-bind:href="externalUrl">Visit Site</a>
</div>
<script>
new Vue({
el: '#root',
data: {
greeting: 'Welcome',
rawText: 'Plain text content',
htmlContent: '<strong>Bold text</strong>',
formInput: '',
externalUrl: 'https://example.com'
}
});
</script>
Conditional Display
Choose between conditional rendering strategies based on frequency of toggling.
<div id="app">
<article v-if="isAuthenticated">Private Content</article>
<aside v-show="isVisible">Collapsible Sidebar</aside>
</div>
<script>
new Vue({
el: '#app',
data: {
isAuthenticated: false,
isVisible: true
}
});
</script>
Note that v-if removes elements from the DOM entirely, incurring higher toggle costs, while v-show uses CSS display properties for efficient visibility switching.
Rendering Lists
Iterate over collections using v-for:
<ul id="list-container">
<li v-for="item in inventory" :key="item.id">
{{ item.product }} - ${{ item.price }}
</li>
</ul>
<script>
new Vue({
el: '#list-container',
data: {
inventory: [
{ id: 1, product: 'Laptop', price: 999 },
{ id: 2, product: 'Mouse', price: 25 },
{ id: 3, product: 'Keyboard', price: 75 }
]
}
});
</script>
Event Handling
Respond to user interactions with the v-on directive or its shorthand:
<div id="events">
<button v-on:click="submitForm">Submit</button>
<button @click="cancelAction">Cancel</button>
</div>
<script>
new Vue({
el: '#events',
methods: {
submitForm() {
console.log('Form submitted');
},
cancelAction() {
console.log('Action cancelled');
}
}
});
</script>
SPA Navigation with Vue Router
Implement client-side routing for single-page applications:
<div id="router-app">
<nav>
<router-link to="/dashboard">Dashboard</router-link>
<router-link to="/profile/123">Profile</router-link>
</nav>
<router-view></router-view>
</div>
<script>
const Dashboard = Vue.extend({
template: '<h2>Dashboard Overview</h2>'
});
const Profile = Vue.extend({
template: '<h2>User: {{ userId }}</h2>',
data() {
return { userId: null };
},
created() {
this.userId = this.$route.params.id;
}
});
const router = new VueRouter({
routes: [
{ path: '/', redirect: '/dashboard' },
{ path: '/dashboard', component: Dashboard },
{ path: '/profile/:id', component: Profile }
]
});
new Vue({
el: '#router-app',
router
});
</script>
Modern JavaScript in Vue Development
Block-scoped declarations prevent variable hoisting issues:
// let prevents redeclaration and avoids hoisting
let count = 1;
// let count = 2; // SyntaxError
// const creates immutable references
const CONFIG = { apiUrl: 'https://api.example.com' };
// CONFIG = {}; // TypeError
// However, object properties remain mutable
CONFIG.timeout = 5000;
Destructuring assignments simplify data extraction:
// Array destructuring
const [first, , third] = [10, 20, 30];
console.log(first, third); // 10 30
// Function return values
function fetchCoordinates() {
return [40.7128, -74.0060];
}
const [lat, lng] = fetchCoordinates();
// Object destructuring
const user = { name: 'Alice', role: 'admin', lastLogin: '2023-01-01' };
const { name, role } = user;
Template literals enable readable string interpolation:
const order = { item: 'Widget', quantity: 5 };
// Concatenation vs Template Literals
const oldWay = '<div class="' + order.item + '">Qty: ' + order.quantity + '</div>';
const newWay = `<div class="${order.item.toLowerCase()}">Qty: ${order.quantity}</div>`;
Arrow functions provide concise syntax and lexical scoping:
const calculateTotal = (price, tax) => price * (1 + tax);
const processItems = (items) => {
const filtered = items.filter(i => i.active);
return filtered.map(i => i.value);
};
The spread operator expands iterables:
const tags = 'vue,js,css';
const tagArray = [...tags.split(',')];
Collection Types
Sets store unique values:
const uniqueIds = new Set([1, 2, 2, 3]);
console.log(uniqueIds.size); // 3
uniqueIds.add(4);
console.log(uniqueIds.has(2)); // true
uniqueIds.delete(1);
uniqueIds.clear();
Maps maintain key-value pairs with any key type:
const userMap = new Map([['id', 101], ['status', 'active']]);
userMap.set('premium', true);
console.log(userMap.get('id'));
userMap.delete('status');
Component Architecture
Parent-to-child communication via props:
<div id="parent-app">
<user-card :username="currentUser" :age="userAge"></user-card>
</div>
<script>
Vue.component('user-card', {
props: {
username: String,
age: Number
},
template: '<div class="card">{{ username }}, {{ age }} years old</div>'
});
new Vue({
el: '#parent-app',
data: {
currentUser: 'JohnDoe',
userAge: 28
}
});
</script>
Child-to-parent communication via custom events:
<div id="event-app">
<notification-banner @dismiss="handleDismiss"></notification-banner>
</div>
<script>
Vue.component('notification-banner', {
template: '<button @click="notifyParent">Close</button>',
methods: {
notifyParent() {
this.$emit('dismiss', { timestamp: Date.now() });
}
}
});
new Vue({
el: '#event-app',
methods: {
handleDismiss(payload) {
console.log('Closed at:', payload.timestamp);
}
}
});
</script>
Development Environment Setup
Initialize a Vue 2 project with webpack:
# Verify Node.js installation
node -v
# Install Vue CLI globally
npm install -g vue-cli
# Create project from webpack template
vue init webpack my-project
# Install dependencies
cd my-project
npm install
# Start development server
npm run dev
Access the application at http://localhost:8080.