Box Model
ถ้ามี mental model อย่างเดียวที่คุณต้องจำก่อนจะเขียน CSS อีกบรรทัด นั่นคือ: ทุก HTML element คือกล่องสี่เหลี่ยม ไม่ใช่แค่บางครั้ง — แต่ทุกครั้ง ไม่ว่าจะเป็น heading, button, รูปภาพ หรือ <div> ที่มองไม่เห็น — ทั้งหมดคือกล่อง และทุกกล่องสร้างจากสี่ชั้นเหมือนกัน เรียงจากในออกนอก
คุณรู้จักชั้นเหล่านี้แล้วจาก Figma CSS แค่ตั้งชื่อให้เท่านั้นเอง
สี่ชั้นของ Box Model
หัวข้อที่มีชื่อว่า “สี่ชั้นของ Box Model”1. Content
หัวข้อที่มีชื่อว่า “1. Content”พื้นที่ชั้นในสุด ที่นี่คือที่อยู่ของข้อความ รูปภาพ หรือ element ลูก คุณควบคุมขนาดด้วย width และ height
.card { width: 320px; height: 200px;}2. Padding
หัวข้อที่มีชื่อว่า “2. Padding”ช่องว่างภายในกล่อง ระหว่าง content กับ border นึกถึง inner spacing ใน Figma auto-layout frame — ดัน content ออกจากขอบโดยไม่เลื่อน element เอง
.card { padding: 2rem; /* ทั้งสี่ด้าน */ padding: 1rem 2rem; /* บน/ล่าง 1rem, ซ้าย/ขวา 2rem */ padding-top: 1rem; /* ด้านเดียว */}3. Border
หัวข้อที่มีชื่อว่า “3. Border”เส้นที่วาดรอบ element — เหมือน Stroke ใน Figma กำหนดความหนา สไตล์ และสี:
.card { border: 2px solid #7C3AED; /* ความหนา สไตล์ สี */ border-radius: 12px; /* มุมโค้งมน */}4. Margin
หัวข้อที่มีชื่อว่า “4. Margin”ช่องว่างภายนอกกล่อง ผลัก element เพื่อนบ้านออกไป ส่วนนี้ไม่ใช่พื้นที่แสดงผลของ element — แต่เป็นช่องว่างล่องหนระหว่างกล่อง นึกถึง gap ระหว่าง frame ใน Figma
.card { margin: 2rem; /* ทุกด้าน */ margin: 1rem 0; /* บน/ล่าง 1rem, ซ้าย/ขวา 0 */ margin-bottom: 1.5rem; /* ด้านเดียว */}ลำดับค่า Shorthand
หัวข้อที่มีชื่อว่า “ลำดับค่า Shorthand”เมื่อให้ค่าสองตัว — padding: 1rem 2rem — ลำดับคือ บน/ล่างก่อน ซ้าย/ขวาตาม สี่ค่าใช้เข็มนาฬิกา: บน, ขวา, ล่าง, ซ้าย
padding: 1rem 2rem 1rem 2rem; /* top right bottom left */กับดัก box-sizing
หัวข้อที่มีชื่อว่า “กับดัก box-sizing”นี่คือจุดที่มือใหม่มักประหลาดใจ โดย default ค่า width ใน CSS วัดเฉพาะ content area ถ้าตั้ง width: 300px แล้วเพิ่ม padding: 20px และ border: 2px solid ความกว้างจริงที่แสดงในหน้าจะเป็น 344px — ไม่ใช่ 300px
นี่คือตรงข้ามกับวิธีที่ design tool ทำงาน ใน Figma ขอบ frame รวม stroke และ inner spacing อยู่แล้ว property box-sizing: border-box ทำให้ CSS ทำงานแบบเดียวกัน: width วัดจากขอบ border ถึงขอบ border — padding และ border รวมอยู่แล้ว ไม่บวกเพิ่ม
/* เพิ่มใน global styles ของทุก project */*, *::before, *::after { box-sizing: border-box;}ด้วย border-box element ที่มี width: 300px จะกว้าง 300px เสมอ ไม่ว่า padding หรือ border จะมากแค่ไหน padding และ border กิน content area แทนการขยายกล่องออกนอก คาดเดาได้ เหมือน Figma
display: block, inline, และ inline-block
หัวข้อที่มีชื่อว่า “display: block, inline, และ inline-block”Box model ทำงานเต็มที่เมื่อ element แสดงเป็น block property display ควบคุมสิ่งนี้:
| ค่า | พฤติกรรม |
|---|---|
block | กินความกว้างทั้งหมด เรียงกันแนวตั้ง Default ของ <div>, <p>, <h1>–<h6> |
inline | อยู่ในกระแสของข้อความ ไม่รองรับ width/height Default ของ <span>, <a>, <strong> |
inline-block | อยู่ในกระแสข้อความแต่รองรับ width, height, padding และ margin เหมาะสำหรับ button และ badge |
นี่คือเหตุผลที่ <div> เรียงต่อจาก element ก่อนหน้าในแนวตั้ง แต่ <span> ไม่เป็นแบบนั้น — หนึ่งคือ block อีกอันคือ inline
ลองแก้ไข CSS: เพิ่ม padding ของ .box, เปลี่ยนความหนา border หรือปรับ width ด้วย box-sizing: border-box ที่ตั้งไว้ ขอบนอกของ .box จะอยู่ที่ 320px เสมอ — content area จะหดเล็กลงเพื่อรับการเปลี่ยนแปลง
ข้อผิดพลาดที่นักออกแบบเจอบ่อย
หัวข้อที่มีชื่อว่า “ข้อผิดพลาดที่นักออกแบบเจอบ่อย”- บอก developer ว่า “กว้าง 300px” โดยไม่ระบุว่ารวม padding/border หรือไม่
- ลืมว่า margin สองฝั่งอาจ collapse กัน
- ไม่คิดถึง box-sizing ตอนวัดขนาดใน Figma
มุมมองของ developer
หัวข้อที่มีชื่อว่า “มุมมองของ developer”👨💻 สิ่งที่ developer เห็นจริง ๆ
หัวข้อที่มีชื่อว่า “👨💻 สิ่งที่ developer เห็นจริง ๆ”Designer เห็น “กรอบสี่เหลี่ยมหนึ่งกรอบ” แต่ developer เห็นสี่ชั้นซ้อนกัน (content, padding, border, margin) ที่ต้องรวมกันให้ได้ขนาดสุดท้ายตรงกับ Figma
💡 ตัวอย่างจากของจริง
Figma’s Inspect panel แสดง padding/margin ที่ map ตรงกับ CSS box model เป๊ะ ช่วยให้ developer copy ค่าไปใช้ได้ทันที