1. ความสำคัญของ Component Reusable
Component Reusable คือ Component ที่ออกแบบมาให้สามารถใช้งานซ้ำได้ในหลายส่วนของโปรเจกต์
- ช่วยลดความซ้ำซ้อนของโค้ด
- เพิ่มความง่ายในการบำรุงรักษา
- ทำให้โครงสร้างโปรเจกต์ชัดเจน
การสร้าง Component Reusable ใน Alpine.js สามารถทำได้โดยการใช้ x-data
, Props, และ Slot
2. การออกแบบ Component พื้นฐาน
ตัวอย่าง 1: ปุ่ม Reusable
<div x-data="{ label: 'Click me', action: () => alert('Button clicked!') }">
<button @click="action" class="px-4 py-2 bg-blue-500 text-white rounded">
<span x-text="label"></span>
</button>
</div>
คำอธิบาย:
- ใช้ State
label
และaction
เพื่อกำหนดข้อความและฟังก์ชัน - สามารถเปลี่ยนค่า
label
และaction
ได้เมื่อใช้งาน Component
3. การใช้ Template เพื่อสร้าง Component Reusable
ตัวอย่าง 2: การสร้าง Card Component
<template id="card-template">
<div class="p-4 border rounded shadow">
<h2 class="text-lg font-bold" x-text="title"></h2>
<p class="text-gray-600" x-text="content"></p>
<button @click="action" class="mt-2 px-4 py-2 bg-blue-500 text-white rounded">
<span x-text="buttonLabel"></span>
</button>
</div>
</template>
<div x-data="{ title: 'Card Title', content: 'This is card content.', buttonLabel: 'Click', action: () => alert('Card clicked!') }">
<div x-init="$el.innerHTML = document.getElementById('card-template').innerHTML"></div>
</div>
คำอธิบาย:
- ใช้
<template>
เพื่อเก็บโครงสร้าง Component - Component สามารถปรับแต่งข้อความและฟังก์ชันได้ด้วย State
4. การสร้าง Component ซ้ำในลูป
ตัวอย่าง 3: วนลูปเพื่อสร้าง Component หลายตัว
<div x-data="{ cards: [
{ title: 'Card 1', content: 'Content for card 1', buttonLabel: 'Click Me', action: () => alert('Card 1 clicked!') },
{ title: 'Card 2', content: 'Content for card 2', buttonLabel: 'Click Me', action: () => alert('Card 2 clicked!') }
] }">
<template x-for="card in cards" :key="card.title">
<div class="p-4 border rounded shadow">
<h2 class="text-lg font-bold" x-text="card.title"></h2>
<p class="text-gray-600" x-text="card.content"></p>
<button @click="card.action" class="mt-2 px-4 py-2 bg-blue-500 text-white rounded">
<span x-text="card.buttonLabel"></span>
</button>
</div>
</template>
</div>
คำอธิบาย:
- ใช้
x-for
วนลูปเพื่อสร้าง Component หลายตัวจากข้อมูลใน Array - แต่ละ Card Component มีค่าของตัวเองที่กำหนดใน Array
5. การใช้ Slot สำหรับ Component Reusable
ตัวอย่าง 4: Component แบบ Slot
<template id="slot-component">
<div class="p-4 border rounded shadow">
<slot></slot>
</div>
</template>
<div>
<div x-data x-init="$el.innerHTML = document.getElementById('slot-component').innerHTML">
<h2 class="text-lg font-bold">Custom Content</h2>
<p>This content is passed to the slot.</p>
</div>
</div>
คำอธิบาย:
- ใช้
<slot>
เพื่อสร้าง Component ที่รองรับเนื้อหาที่กำหนดเอง - สามารถส่งเนื้อหาเข้ามาใน Component ผ่านโครงสร้าง HTML
6. การส่ง Props ให้ Component Reusable
ตัวอย่าง 5: Component พร้อม Props
<div x-data="{ createButton(label, action) { return { label, action }; } }">
<template x-data="createButton('Submit', () => alert('Submitted!'))">
<button @click="action" class="px-4 py-2 bg-green-500 text-white rounded">
<span x-text="label"></span>
</button>
</template>
</div>
คำอธิบาย:
- ฟังก์ชัน
createButton
สร้าง State สำหรับ Component - สามารถส่ง
label
และaction
เป็น Props เพื่อกำหนดค่าของปุ่ม
7. การจัดการ State ร่วมกันใน Component
ตัวอย่าง 6: ใช้ Alpine.store สำหรับ State ร่วมกัน
<script>
document.addEventListener('alpine:init', () => {
Alpine.store('sharedState', {
count: 0
});
});
</script>
<div>
<div x-data>
<button @click="$store.sharedState.count++">Increment</button>
</div>
<div x-data>
<p>Shared Count: <span x-text="$store.sharedState.count"></span></p>
</div>
</div>
คำอธิบาย:
- ใช้
Alpine.store
เพื่อจัดการ State ที่แชร์ระหว่าง Component - ลดความซ้ำซ้อนในการประกาศ State เดียวกันในหลาย Component
8. การสร้าง Component Reusable ที่ยืดหยุ่น
ตัวอย่าง 7: Component แบบ Dynamic
<div x-data="{ createCard(title, content, buttonLabel, action) {
return { title, content, buttonLabel, action };
}, cards: [] }">
<button @click="cards.push(createCard('Dynamic Title', 'Dynamic Content', 'Click Me', () => alert('Dynamic Clicked!')))">
Add Card
</button>
<template x-for="card in cards" :key="card.title">
<div class="p-4 border rounded shadow">
<h2 class="text-lg font-bold" x-text="card.title"></h2>
<p class="text-gray-600" x-text="card.content"></p>
<button @click="card.action" class="mt-2 px-4 py-2 bg-blue-500 text-white rounded">
<span x-text="card.buttonLabel"></span>
</button>
</div>
</template>
</div>
คำอธิบาย:
- ฟังก์ชัน
createCard
สร้างข้อมูลสำหรับ Card Component - สามารถเพิ่ม Card ใหม่ได้แบบ Dynamic
สรุป
ในบทนี้ คุณได้เรียนรู้การสร้าง Component Reusable ใน Alpine.js ตัวอย่างครอบคลุมการสร้าง Component แบบฟังก์ชัน, การใช้ Slot, การส่ง Props, และการแชร์ State Component Reusable ช่วยลดการเขียนโค้ดซ้ำ เพิ่มความยืดหยุ่น และทำให้การพัฒนาโปรเจกต์มีประสิทธิภาพมากขึ้น!