ออปติไมซ์รูปภาพเว็บไซต์แบรนด์: บีบอัดอัตโนมัติ, WebP/AVIF, Lazy Load และ CDN
หนึ่ง: ทำไมรูปภาพถึงเป็นตัวฆ่าประสิทธิภาพอันดับหนึ่งของเว็บไซต์แบรนด์
สถิติจาก HTTP Archive แสดงว่าโดยเฉลี่ยแล้วรูปภาพคิดเป็นสัดส่วนเกิน 50% ของปริมาณข้อมูลที่ส่งทั้งหมดในหนึ่งหน้าเว็บ และสำหรับเว็บไซต์แบรนด์ B2B ที่มีรูปสินค้า รูปเคส และรูปโรงงานหนาแน่น สัดส่วนนี้มักพุ่งถึง 60% ถึง 70% ข้อความกับ CSS รวมกันอาจแค่ 100KB แต่ banner สินค้าที่ไม่ได้บีบอัดหนึ่งรูปอาจหนัก 2 ถึง 3MB
หลุมที่ทีมเว็บไซต์แบรนด์ตกบ่อยที่สุดคือ: ดีไซเนอร์ export รูปต้นฉบับจาก PSD แล้วอัปโหลดเข้า WordPress ตรงๆ ตอนอัปโหลดไม่ย่อขนาด และธีมก็ไม่สร้าง WebP ผลคือหน้ารายละเอียดสินค้าหนึ่งหน้ามีรูปใหญ่ 2MB แปดรูป บนเครือข่าย 3G ฝั่งมือถือแค่รูปก็ใช้เวลาโหลด 30 วินาที ผู้เข้าชมปิดหน้าก่อนที่รูปจะแสดงด้วยซ้ำ วิธีจัดการสินทรัพย์มีเดียดูได้ที่การจัดการสินทรัพย์สื่อ เกณฑ์ผ่าน Core Web Vitals กำหนดอย่างไร ดูได้ที่การปรับแต่ง Core Web Vitals。
| ปัญหาภาพที่พบบ่อย | ผลกระทบต่อประสิทธิภาพ | ลำดับความสำคัญในการแก้ |
|---|---|---|
| อัปโหลดรูปต้นฉบับโดยไม่ย่อขนาด | รูปเดียว 2 ถึง 3MB ทำให้ LCP เกินเกณฑ์ทันที | สูงสุด แก้ภายในสัปดาห์นี้ |
| ใช้แค่ JPEG ไม่มี WebP | คุณภาพเท่ากันแต่ขนาดใหญ่กว่า 30% ถึง 50% | สูง ภายในสองสัปดาห์ |
| ตั้ง Lazy Load ให้ banner หน้าแรก | LCP ช้าลง 1 ถึง 2 วินาที | สูงสุด แก้ทันที |
| ขาดแอตทริบิวต์ width/height | CLS (Cumulative Layout Shift) | ปานกลาง อัปเดตตามธีม |
| รูปไม่ได้ผ่าน CDN | ดึงข้อมูลข้ามทวีปช้า 1 ถึง 3 วินาที | สูง ตั้งค่าควบคู่กับ CDN |
สอง: บีบอัดอัตโนมัติ สี่เส้นทางที่จัดการทันทีเมื่ออัปโหลด
การบีบอัดรูปไม่ควรให้ทีมปฏิบัติการนั่งบีบทีละรูปด้วยมือ แต่ต้องทำอัตโนมัติในขั้นตอนอัปโหลด ระบบนิเวศ WordPress มีสามเส้นทางสำเร็จรูป: Smush, ShortPixel, Imagify ทั้งหมดบีบอัดอัตโนมัติและสร้าง WebP ตอนอัปโหลด ค่าบริการรายปี 50 ถึง 100 ดอลลาร์สหรัฐฯ ขึ้นอยู่กับแพ็กเกจ หากเว็บไซต์แบรนด์มีรูปไม่เกิน 500 รูปต่อปี เลือกแพ็กเกจที่ถูกที่สุดก็เพียงพอ
คุณภาพการบีบอัดมีค่าที่ใช้ได้จริง: JPEG คุณภาพ 75 ถึง 82 คือจุดสมดุลระหว่างตาเปล่ากับขนาดไฟล์ ต่ำกว่า 70 จะเกิดรอยบล็อกและขอบหยัก สูงกว่า 85 ขนาดไฟล์ที่ลดได้จะเริ่มน้อยลงแบบไม่คุ้ม ส่วน PNG ถ้ามีช่องโปร่งใสให้ใช้ quantization ลดเหลือ 16 ถึง 32 สี ขนาดไฟล์จะลดได้มากกว่า 60% ตัวอย่างจริง: รูปถ่ายในโรงงานอุตสาหกรรมที่ JPEG คุณภาพ 78 ความกว้าง 1920 ส่งออกมาแล้วมักอยู่ที่ 150 ถึง 220KB ถ้าเกิน 300KB แสดงว่าการครอปหรือระดับคุณภาพยังมีปัญหา เรื่องวิธีเลือก CDN ดูได้ที่เปรียบเทียบการเลือก CDN。
| ประเภทภาพ | รูปแบบที่แนะนำ | ขนาดเป้าหมาย | ความกว้างสูงสุด |
|---|---|---|---|
| ภาพ banner/hero หน้าแรก | WebP + JPEG สำรอง | 150 ถึง 200KB | 1920px |
| ภาพสินค้าหลัก | WebP + JPEG สำรอง | 80 ถึง 120KB | 1200px |
| ภาพสินค้าย่อ | WebP | 15 ถึง 30KB | 300px |
| ภาพประกอบเคส/บทความ | WebP | 80 ถึง 150KB | 1200px |
| ไอคอน/โลโก้ | SVG หรือ PNG ขนาดเล็ก | ไม่เกิน 5KB | 2 เท่าของขนาดที่แสดง |
| ภาพแคปหน้าจอ/ภาพที่มีข้อความ | PNG ไม่บีบคุณภาพ | ได้ถึง 200KB | 2 เท่าของความกว้างที่แสดง |
สาม、วิธีตั้งค่า WebP/AVIF: แท็ก picture กับการเจรจาอัตโนมัติของ CDN
WebP รองรับใน Chrome/Edge/Firefox/Safari 14 ขึ้นไป อัตราครอบคลุมเกิน 95% แล้ว ส่วน AVIF บีบอัดได้สูงกว่า WebP อีก 20% ถึง 30% แต่ Safari ต้องรองรับถึง 16.4 การเข้ารหัสช้า เหมาะกับภาพนิ่งที่สร้างล่วงหน้าเป็นชุด เว็บไซต์อิสระไม่จำเป็นต้องเขียน AVIF เอง ปล่อยให้ CDN แปลงรหัสอัตโนมัติตาม Accept header ตอนดึงจากต้นทางจะสะดวกกว่า
มีสองวิธีทำ วิธีแรกคือให้ CDN เจรจาอัตโนมัติ: Cloudflare, Cloudinary และ Fastly ต่างรองรับการส่ง WebP หรือ AVIF กลับอัตโนมัติตาม Accept header โดยต้นทางเก็บแค่ JPEG/PNG ทีมปฏิบัติการไม่ต้องแก้อะไร วิธีที่สองคือฝั่ง frontend ประกาศชัดเจนด้วยแท็ก picture เหมาะกับเว็บเล็กที่ยังไม่ใช้ CDN ข้อสังเกตที่ขัดกับสัญชาตญาณคือ อย่าเข้ารหัสภาพทั้งหมดใหม่เพื่อตาม AVIF เวลาการเข้ารหัส AVIF มากกว่า WebP 5 ถึง 10 เท่า ถ้าจำนวนภาพไม่ต่ำกว่า 500 ภาพ ต้นทุนจะไม่คุ้ม วิธีตั้งค่าการเร่งความเร็วทั่วโลก ดูที่CDN เร่งความเร็วทั่วโลก。
| 方案 | วิธีทำ | การรองรับของเบราว์เซอร์ | ต้นทุนต่อปี | เหมาะกับ |
|---|---|---|---|---|
| CDN แปลงรหัสอัตโนมัติ | Cloudflare/Cloudinary ส่งรูปแบบตาม Accept header | ลดระดับอัตโนมัติ 95%+ | รวมอยู่ในค่า CDN | ตัวเลือกแรกของเว็บอิสระส่วนใหญ่ |
| แท็ก Picture สองรูปแบบ | เขียน <picture> + WebP/JPEG เอง | ควบคุมด้วยมือ | 0 ดอลลาร์ | เว็บเล็กที่ยังไม่ใช้ CDN |
| ปลั๊กอิน WordPress สร้างอัตโนมัติ | ShortPixel/Smush สร้างสำเนา WebP | 95%+ | 50 ถึง 100 ดอลลาร์/ปี | เว็บอิสระ WordPress |
| สร้าง AVIF ล่วงหน้าทั้งเว็บ | แปลง AVIF เป็นชุดตอน build | ประมาณ 85% | ต้นทุนการเข้ารหัสสูง | เว็บแบรนด์ที่มีภาพ <500 ภาพ |
| เก็บแค่ JPEG | ไม่ใช้รูปแบบสมัยใหม่ | 100% | 0 ดอลลาร์ | ยังไม่แนะนำ เสียเปรียบเรื่องขนาด |
สี่、srcset กับภาพตอบสนอง: อย่าให้มือถือดาวน์โหลดภาพเดสก์ท็อป
บีบอัดอย่างเดียวยังไม่พอ ต้องให้เบราว์เซอร์เลือกภาพตามขนาดหน้าจอด้วย banner กว้าง 1920px บนมือถือแสดงแค่ 375px แต่ยังดาวน์โหลด 200KB เท่ากับเสียทราฟฟิก 70% วิธีที่ถูกต้องคือใช้ srcset+sizes ประกาศหลายขนาด เบราว์เซอร์จะเลือกภาพที่เหมาะสมที่สุดอัตโนมัติตาม device pixel ratio และความกว้าง viewport
WordPress จะสร้างขนาดย่อหลายแบบอัตโนมัติเมื่ออัปโหลด (thumbnail, medium, large) แต่ธีมอาจไม่ได้ใช้ srcset ในเทมเพลต วิธีตรวจแบบเจาะจง: เปิด Chrome DevTools Network ดู URL รูปที่ดาวน์โหลดจริงของแบนเนอร์หน้าแรก ถ้าได้รูป 1920px ตลอด แสดงว่า srcset ไม่ทำงาน วิธีแก้ที่ต้นทุนต่ำสุดคือเปิดใช้ add_image_size ใน functions.php ของธีม และให้ the_post_thumbnail ส่งออก srcset ไม่ต้องเขียนแท็กเอง
| เบรกพอยต์ | ความกว้างที่แนะนำ | ใช้ทำอะไร |
|---|---|---|
| มือถือแนวตั้ง | 640px | ลิสต์และบทความบนมือถือ |
| แท็บเล็ตแนวตั้ง | 1024px | แท็บเล็ตและเดสก์ท็อปจอเล็ก |
| เดสก์ท็อป | 1920px | แบนเนอร์และภาพประกอบแบบกว้าง |
| Retina 2x | ตามความกว้างที่แสดง ×2 | จอความละเอียดสูงไม่เบลอ |
ห้า、Lazy Load: นอกจอแรก lazy ทั้งหมด รูปจอแรกต้อง eager
Native Lazy Load ใช้งานได้เต็มที่แล้ว Chrome/Firefox/Safari 15.4 ขึ้นไปรองรับ กฎง่ายมาก: รูปที่อยู่ในวิวพอร์ตจอแรก (ปกติคือแบนเนอร์จอแรก รูปสินค้ารูปแรก) ต้อง loading=”eager” ที่เหลือทั้งหมด loading=”lazy” WordPress ตั้งแต่ 5.5 ใส่ lazy ให้รูปในเนื้อหาเป็นค่าเริ่มต้น แต่แบนเนอร์จอแรกที่ฮาร์ดโค้ดในธีมต้องแก้เป็น eager ด้วยมือ
พฤติกรรมทำร้ายตัวเองที่พบบ่อยที่สุดคือ: เพื่อ “เพิ่มประสิทธิภาพ” ตั้งแบนเนอร์จอแรกเป็น lazy ด้วย ผลคือเบราว์เซอร์ต้องรอให้ HTML parse ถึงแท็กรูปก่อนจึงเริ่มร้องขอ องค์ประกอบ LCP ถูกเลื่อนออกไป 1 ถึง 2 วินาที วิธีที่ถูกต้องคือใช้ <link rel=”preload” as=”image”> โหลดแบนเนอร์จอแรกไว้ล่วงหน้า พร้อมคงแอตทริบิวต์ width/height ไว้กัน CLS ตัวอย่างการตั้งค่าจริง: เพิ่ม <link rel=”preload” as=”image” href=”hero.webp” fetchpriority=”high”> ใน head สำหรับรูป hero หน้าแรก ช่วยกด LCP ได้อีก 0.5 วินาที ดูนโยบายแคชของเว็บไซต์ได้ที่นโยบายแคชของเว็บไซต์。
| ตำแหน่งรูป | แอตทริบิวต์ loading | fetchpriority | preload |
|---|---|---|---|
| hero/แบนเนอร์จอแรก | eager (ไม่เขียน lazy) | high | ต้องใส่ rel=preload |
| รูปสินค้าหลักในจอแรก | eager | high หรือ auto | ใส่ preload ตามความเหมาะสม |
| รูปประกอบบทความใต้จอแรก | lazy | low หรือไม่ใส่ | ไม่ใส่ |
| รูปย่อหน้ารายการ | lazy | ไม่ระบุ | ไม่ใส่ |
| ฟุตเตอร์/โลโก้/รูปตกแต่ง | lazy | low | ไม่ใส่ |
หก、ตรวจรับ: มองสองมุมด้วย Lighthouse และ RUM
ทำรูปให้เสร็จแล้วดูแค่คะแนน Lighthouse ไม่ได้ เพราะข้อมูลจากแล็บกับข้อมูลผู้ใช้จริงจะต่างกัน Lighthouse ดูหลักสามอย่าง: รูปที่ยังไม่ปรับแต่ง รูปที่ขนาดถูกต้อง และรูปฟอร์แมตสมัยใหม่ ว่า audit ทั้งสามเขียวหมดหรือไม่ ข้อมูลผู้ใช้จริงดูเปอร์เซ็นไทล์ที่ 75 ของ LCP ผ่าน CrUX (Chrome User Experience Report) หรือ Cloudflare RUM อย่าดูค่าเฉลี่ย เพราะค่าเฉลี่ยจะถูกผู้ใช้ที่เร็วไม่กี่คนดึงต่ำลง เปอร์เซ็นไทล์ที่ 75 ต่างหากที่สะท้อนความรู้สึกจริงของคนเข้าชมส่วนใหญ่
เช็กลิสต์ตรวจรับที่ทำได้จริง: รูป LCP หน้าแรก ≤200KB, รูปนอกจอแรกทั้งเว็บ lazy 100%, รูปทั้งหมดมี width/height, WebP/AVIF ครอบคลุม ≥90%, ไบต์รูปรวมต่อหน้า ≤1MB ถ้าไม่ถึงให้กลับไปปรับตามหัวข้อที่เกี่ยวข้อง การปรับ PHP และฐานข้อมูลเป็นอีกสายหนึ่ง ดูที่อัปเกรดเวอร์ชัน PHP และ ปรับ slow query ของฐานข้อมูล。
| ตัวชี้วัดการยอมรับ | เกณฑ์ผ่าน | เครื่องมือวัด | วิธีจัดการเมื่อไม่ผ่านเกณฑ์ |
|---|---|---|---|
| ขนาดไฟล์ภาพ LCP | ≤200KB | Lighthouse/DevTools | บีบอัดหรือครอป |
| อัตราครอบคลุม WebP/AVIF | ≥90% | ดู response header ใน DevTools Network | เปิด auto convert ที่ CDN |
| อัตราครอบคลุม lazy load | 100% ของภาพนอกจอแรก | ตรวจ attribute loading ในซอร์สโค้ด | แทนที่ในเทมเพลตแบบเป็นชุด |
| การระบุขนาดภาพ | 100% มี width/height | Lighthouse CLS audit | เติม attribute ให้ครบทั้งเทมเพลต |
| ไบต์รวมของภาพในหนึ่งหน้า | ≤1MB | DevTools Network | ลบภาพซ้ำซ้อนหรือรวมเป็น sprite |
| LCP เปอร์เซ็นไทล์ที่ 75 | ≤2.5 วินาที | CrUX/Cloudflare RUM | ดูว่าเป็นปัญหาที่ภาพหรือฟอนต์ |
FAQ คำถามที่พบบ่อย
WebP กับ AVIF ควรใช้ตัวไหน?
ตั้ง lazy load ให้ banner จอแรกได้ไหม?
บีบอัดคุณภาพภาพเหลือเท่าไรตาจึงแยกไม่ออก?
ปลั๊กอินบีบอัดอัตโนมัติของ WordPress เลือกตัวไหน?
ภาพที่ผ่าน CDN กับไม่ผ่านต่างกันแค่ไหน?
หลังปรับแต่งภาพแล้ว ตรวจรับอย่างไรจึงจะถือว่าผ่าน?
ทิ้งท้าย
การ optimize รูปไม่ใช่โปรเจกต์ทำครั้งเดียว แต่เป็นไปป์ไลน์ที่ประมวลผลทันทีที่อัปโหลด วิธีที่ประหยัดแรงจริงคือฝังกฎไว้ในขั้นตอนอัปโหลด: ความกว้างสูงสุด 1920, คุณภาพ JPEG 80, สร้าง WebP อัตโนมัติ, รูปนอกจอแรก lazy อัตโนมัติ, CDN เจรจารูปแบบอัตโนมัติ หลังจากนี้ทีมปฏิบัติการแค่วาดรูปมาวางอัปโหลด ไม่ต้องจำกฎใด ๆ พอไปป์ไลน์นี้ทำงานได้ รูปใหม่ที่เพิ่มเข้ามาจะผ่านเกณฑ์อัตโนมัติ ไม่ต้องตรวจด้วยมือทุกครั้ง
ลงมือ 3 ขั้น: หนึ่ง สัปดาห์นี้รัน Lighthouse กับหน้าแรกหนึ่งรอบ ดู audit รูปที่ยังไม่ optimize กับรูปแบบสมัยใหม่ สอง ติดตั้งปลั๊กอินบีบอัดอัตโนมัติอย่าง ShortPixel หรือ Smush แล้วเปิดสร้าง WebP สาม ใส่ preload ให้แบนเนอร์จอแรก ที่เหลือใส่ lazy กับ width/height แบบเป็นชุด สองสัปดาห์แล้ววัด LCP เปอร์เซ็นไทล์ 75 อีกครั้ง
ประโยคเดียวที่จำได้: เป้าหมายของการ optimize รูปไม่ใช่ “เล็ก” แต่คือทำให้รูปหลักที่เป็น LCP แสดงภายใน 2.5 วินาที ส่วนรูปอื่นจะใหญ่แค่ไหนก็รอได้
