การตัดข้อความรอบเส้นทางที่กำหนดเอง
เป็นเวลานานแล้วที่นักออกแบบเว็บไซต์ถูกบังคับให้สร้างสรรค์ผลงานภายในข้อจำกัดของสี่เหลี่ยมผืนผ้า เนื้อหาส่วนใหญ่บนเว็บยังคงติดอยู่ในกล่องสี่เหลี่ยมธรรมดาๆ เนื่องจากความพยายามสร้างสรรค์เลย์เอาต์ที่ไม่ใช่สี่เหลี่ยมผืนผ้าส่วนใหญ่มักจบลงด้วยความหงุดหงิด แต่สิ่งนี้กำลังจะเปลี่ยนไปด้วยการเปิดตัว CSS Shapes ซึ่งพร้อมใช้งานตั้งแต่ Chrome 37 เป็นต้นไป รูปร่าง CSS ช่วยให้นักออกแบบเว็บไซต์สามารถตัดข้อความรอบเส้นทางที่กำหนดเองได้ เช่น วงกลม วงรี และรูปหลายเหลี่ยม จึงหลุดพ้นจากข้อจำกัดของสี่เหลี่ยมผืนผ้า
คุณสามารถกำหนดรูปร่างด้วยตนเองหรืออนุมานจากรูปภาพก็ได้
มาดูตัวอย่างง่ายๆ กัน
คุณอาจเคยไร้เดียงสาเหมือนฉันเมื่อครั้งแรกที่ลอยรูปภาพที่มีส่วนโปร่งใสโดยคาดหวังว่าเนื้อหาจะตัดขึ้นบรรทัดใหม่และเติมเต็มช่องว่าง แต่ก็ต้องผิดหวังกับรูปร่างการตัดขึ้นบรรทัดใหม่สี่เหลี่ยมผืนผ้าที่ยังคงอยู่รอบองค์ประกอบ คุณสามารถใช้ CSS Shapes เพื่อแก้ปัญหานี้ได้
<img class="element" src="image.png" />
<p>Lorem ipsum…</p>
<style>
.element{
shape-outside: url(image.png);
shape-image-threshold: 0.5;
float: left;
}
</style>
การประกาศ CSS shape-outside: url(image.png) จะบอกให้เบราว์เซอร์ดึงรูปร่างออกจากรูปภาพ
พร็อพเพอร์ตี้ shape-image-threshold กำหนดระดับความทึบแสงขั้นต่ำของพิกเซลที่จะใช้สร้างรูปร่าง ค่าต้องอยู่ในช่วงระหว่าง 0.0 (โปร่งใสสุด) ถึง 1.0 (ทึบแสงสุด) ดังนั้น shape-image-threshold: 0.5 หมายความว่าระบบจะใช้เฉพาะพิกเซลที่มีความทึบแสง 50% ขึ้นไปเพื่อสร้างรูปร่าง
พร็อพเพอร์ตี้ float เป็นกุญแจสำคัญในที่นี้ แม้ว่าพร็อพเพอร์ตี้ shape-outside จะกำหนดรูปร่างของพื้นที่ที่เนื้อหาจะตัดขึ้นบรรทัดใหม่ แต่หากไม่มีการลอย คุณจะไม่เห็นผลลัพธ์ของรูปร่าง
องค์ประกอบมีพื้นที่ลอยอยู่ฝั่งตรงข้ามกับค่า float ตัวอย่างเช่น หากองค์ประกอบที่มีรูปภาพถ้วยกาแฟลอยอยู่ทางซ้าย ระบบจะสร้างพื้นที่ลอยทางด้านขวาของถ้วย แม้ว่าคุณจะออกแบบรูปภาพที่มีช่องว่างทั้ง 2 ด้านได้ แต่เนื้อหาจะตัดขึ้นบรรทัดใหม่ตามรูปร่างในด้านตรงข้ามที่กำหนดโดยพร็อพเพอร์ตี้ Float เท่านั้น ไม่ว่าจะเป็นด้านซ้ายหรือขวา แต่จะไม่ใช่ทั้ง 2 ด้าน
ในอนาคต คุณจะใช้ shape-outside กับองค์ประกอบที่ไม่ลอยได้ด้วยการเปิดตัว CSS Exclusions
การสร้างรูปร่างด้วยตนเอง
นอกจากการดึงรูปร่างจากรูปภาพแล้ว คุณยังเขียนโค้ดรูปร่างด้วยตนเองได้ด้วย คุณเลือกค่าฟังก์ชันได้ 2-3 ค่าเพื่อสร้างรูปร่าง ได้แก่ circle(), ellipse(), inset() และ polygon() ฟังก์ชันรูปร่างแต่ละฟังก์ชันจะยอมรับชุดพิกัดและจับคู่กับกล่องอ้างอิงซึ่งสร้างระบบพิกัด เราจะพูดถึงช่องอ้างอิงเพิ่มเติมในอีกสักครู่
ฟังก์ชัน circle()
สัญกรณ์แบบเต็มสำหรับค่ารูปร่างวงกลมคือ circle(r at cx cy) โดยที่ r คือรัศมีของวงกลม ส่วน cx และ cy คือพิกัดของจุดศูนย์กลางวงกลมบนแกน X และแกน Y พิกัดของจุดศูนย์กลางวงกลมจะมีหรือไม่ก็ได้ หากคุณไม่ระบุ ระบบจะใช้จุดกึ่งกลางขององค์ประกอบ (จุดตัดของเส้นทแยงมุม) เป็นค่าเริ่มต้น
.element{
shape-outside: circle(50%);
width: 300px;
height: 300px;
float: left;
}
ในตัวอย่างด้านบน เนื้อหาจะตัดขึ้นบรรทัดใหม่รอบๆ ด้านนอกของเส้นทางวงกลม อาร์กิวเมนต์เดียว 50% จะระบุรัศมีของวงกลม ซึ่งในกรณีนี้จะเท่ากับครึ่งหนึ่งของความกว้างหรือความสูงขององค์ประกอบ การเปลี่ยนขนาดขององค์ประกอบจะส่งผลต่อรัศมีของรูปทรงวงกลม นี่เป็นตัวอย่างพื้นฐานของวิธีที่รูปร่าง CSS สามารถปรับเปลี่ยนตามอุปกรณ์ได้
ก่อนที่จะดำเนินการต่อ โปรดทราบว่ารูปร่าง CSS มีผลต่อรูปร่างของพื้นที่ลอยรอบองค์ประกอบเท่านั้น หากองค์ประกอบมีพื้นหลัง รูปร่างจะไม่ครอบตัดพื้นหลังนั้น หากต้องการให้ได้ผลลัพธ์ดังกล่าว คุณต้องใช้พร็อพเพอร์ตี้จากการมาสก์ CSS ไม่ว่าจะเป็น clip-path หรือ mask-image พร็อพเพอร์ตี้ clip-path มีประโยชน์มากเนื่องจากใช้รูปแบบเดียวกับรูปร่าง CSS คุณจึงนำค่ามาใช้ซ้ำได้
ภาพประกอบในเอกสารนี้ใช้การคลิปเพื่อไฮไลต์รูปร่างและช่วยให้คุณเข้าใจผลลัพธ์
กลับไปที่รูปทรงวงกลม
เมื่อใช้เปอร์เซ็นต์สำหรับรัศมีวงกลม ระบบจะคำนวณค่าด้วยสูตรที่ซับซ้อนกว่าเล็กน้อย: sqrt(width^2 + height^2) / sqrt(2) การทำความเข้าใจเรื่องนี้จะเป็นประโยชน์เพราะจะช่วยให้คุณจินตนาการได้ว่ารูปร่างวงกลมที่ได้จะเป็นอย่างไรหากขนาดขององค์ประกอบไม่เท่ากัน
คุณสามารถใช้หน่วย CSS ทุกประเภทในพิกัดฟังก์ชันรูปร่างได้ เช่น px, em, rem, vw, vh และอื่นๆ คุณสามารถเลือกรูปแบบที่มีความยืดหยุ่นหรือเข้มงวดเพียงพอสำหรับความต้องการของคุณ
คุณปรับตำแหน่งของวงกลมได้โดยตั้งค่าที่ชัดเจนสำหรับพิกัดของจุดศูนย์กลาง
.element{
shape-outside: circle(50% at 0 0);
}
ซึ่งจะวางจุดศูนย์กลางของวงกลมไว้ที่จุดเริ่มต้นของระบบพิกัด ระบบพิกัดคืออะไร นี่คือส่วนที่เราจะแนะนำกล่องอ้างอิง
กล่องอ้างอิงสำหรับรูปร่าง CSS
กล่องอ้างอิงคือกล่องเสมือนรอบองค์ประกอบ ซึ่งสร้างระบบพิกัดที่ใช้ในการวาดและจัดตำแหน่งรูปร่าง จุดเริ่มต้นของระบบพิกัดอยู่ที่มุมซ้ายบน โดยมีแกน X ชี้ไปทางขวาและแกน Y ชี้ลง
โปรดทราบว่า shape-outside จะเปลี่ยนรูปร่างของพื้นที่ลอยซึ่งเนื้อหาจะตัดขึ้นบรรทัดใหม่ พื้นที่ลอยจะขยายไปยังขอบด้านนอกของกล่องที่กำหนดโดยพร็อพเพอร์ตี้ margin ซึ่งเรียกว่า margin-box และเป็นกล่องอ้างอิงเริ่มต้นสำหรับรูปร่างหากไม่มีการระบุไว้อย่างชัดเจน
การประกาศ CSS 2 รายการต่อไปนี้ให้ผลลัพธ์เหมือนกัน
.element{
shape-outside: circle(50% at 0 0);
/* identical to: */
shape-outside: circle(50% at 0 0) margin-box;
}
เรายังไม่ได้ตั้งค่าระยะขอบในองค์ประกอบ ในตอนนี้ คุณสามารถสรุปได้ว่าจุดเริ่มต้นของระบบพิกัดและจุดศูนย์กลางของวงกลมอยู่ที่มุมซ้ายบนของพื้นที่เนื้อหาขององค์ประกอบ แต่จะเปลี่ยนไปเมื่อคุณกำหนดมาร์จิ้น ดังนี้
.element{
shape-outside: circle(50% at 0 0) margin-box;
margin: 100px;
}
ตอนนี้จุดเริ่มต้นของระบบพิกัดอยู่นอกพื้นที่เนื้อหาขององค์ประกอบ (ขึ้นไป 100 พิกเซลและไปทางซ้าย 100 พิกเซล) เช่นเดียวกับจุดศูนย์กลางของวงกลม ค่าที่คำนวณได้ของรัศมีวงกลมจะเพิ่มขึ้นด้วยเพื่อพิจารณาพื้นผิวที่เพิ่มขึ้นของระบบพิกัดที่สร้างขึ้นโดยกล่องอ้างอิง margin-box
คุณใช้ช่องอ้างอิงได้เพียง 1 ช่องในแต่ละครั้งที่มีการประกาศ shape-outside กล่องอ้างอิงแต่ละกล่องจะส่งผลต่อรูปร่างในลักษณะที่แตกต่างกันและบางครั้งก็ละเอียดอ่อน มีบทความอีกบทความหนึ่งที่เจาะลึกและช่วยให้คุณเข้าใจกล่องอ้างอิงสำหรับรูปร่าง CSS
ฟังก์ชัน ellipse()
วงรีมีลักษณะเหมือนวงกลมที่ถูกบีบ โดยกำหนดเป็น ellipse(rx ry at cx cy) โดยที่ rx และ ry คือรัศมีของวงรีบนแกน X และแกน Y ส่วน cx และ cy คือพิกัดของจุดศูนย์กลางของวงรี
.element{
shape-outside: ellipse(150px 300px at 50% 50%);
width: 300px;
height: 600px;
}
ระบบจะคำนวณค่าเปอร์เซ็นต์จากมิติข้อมูลของระบบพิกัด ไม่ต้องใช้คณิตศาสตร์ที่ซับซ้อน คุณสามารถละเว้นพิกัดสำหรับจุดศูนย์กลางวงรีได้ และระบบจะอนุมานพิกัดจากจุดศูนย์กลางของระบบพิกัด
นอกจากนี้ยังกำหนดรัศมีบนแกน X และ Y ด้วยคีย์เวิร์ดได้ด้วย โดย farthest-side จะให้รัศมีเท่ากับระยะห่างระหว่างจุดศูนย์กลางของวงรีกับด้านของกล่องอ้างอิงที่อยู่ห่างจากจุดศูนย์กลางมากที่สุด ส่วน closest-side หมายถึงสิ่งที่ตรงกันข้าม นั่นคือใช้ระยะห่างที่สั้นที่สุดระหว่างจุดศูนย์กลางกับด้านหนึ่ง
.element{
shape-outside: ellipse(closest-side farthest-side at 50% 50%);
/* identical to: */
shape-outside: ellipse(150px 300px at 50% 50%);
width: 300px;
height: 600px;
}
ซึ่งอาจมีประโยชน์เมื่อขนาดขององค์ประกอบ (หรือกล่องอ้างอิง) อาจเปลี่ยนแปลงในลักษณะที่คาดเดาไม่ได้ แต่คุณต้องการให้รูปร่างวงรีปรับเปลี่ยนตาม
นอกจากนี้ คุณยังใช้คีย์เวิร์ด farthest-side และ closest-side เดียวกันสำหรับรัศมีในฟังก์ชันรูปร่าง circle() ได้ด้วย
ฟังก์ชัน polygon()
หากวงกลมและวงรีมีข้อจำกัดมากเกินไป ฟังก์ชันรูปร่างรูปหลายเหลี่ยมจะช่วยเปิดโลกแห่งตัวเลือกใหม่ๆ รูปแบบคือ polygon(x1 y1, x2 y2, ...) โดยคุณต้องระบุคู่พิกัด x y สำหรับจุดยอด (จุด) แต่ละจุดของรูปหลายเหลี่ยม จำนวนคู่ขั้นต่ำในการระบุรูปหลายเหลี่ยมคือ 3 คู่ ซึ่งก็คือรูปสามเหลี่ยม
.element{
shape-outside: polygon(0 0, 0 300px, 300px 600px);
width: 300px;
height: 600px;
}
จุดยอดจะอยู่บนระบบพิกัด สำหรับรูปหลายเหลี่ยมที่ปรับเปลี่ยนตามพื้นที่โฆษณา คุณสามารถใช้ค่าเปอร์เซ็นต์สำหรับพิกัดบางส่วนหรือทั้งหมดได้
.element{
/* polygon responsive to font-size*/
shape-outside: polygon(0 0, 0 100%, 100% 100%);
width: 20em;
height: 40em;
}
มีพารามิเตอร์ fill-rule ที่ไม่บังคับ ซึ่งนำเข้าจาก SVG ซึ่งจะบอกเบราว์เซอร์ถึงวิธีพิจารณา "ความเป็นภายใน" ของรูปหลายเหลี่ยมในกรณีที่มีเส้นทางที่ตัดกันเองหรือรูปร่างที่ปิดล้อม Joni Trythall อธิบายวิธีการทำงานของพร็อพเพอร์ตี้ fill-rule ใน SVG ได้เป็นอย่างดี หากไม่ได้กำหนดไว้ fill-rule จะมีค่าเริ่มต้นเป็น nonzero
.element{
shape-outside: polygon(0 0, 0 100%, 100% 100%);
/* identical to: */
shape-outside: polygon(nonzero, 0 0, 0 100%, 100% 100%);
}
ฟังก์ชัน inset()
ฟังก์ชันรูปร่าง inset() ช่วยให้คุณสร้างรูปร่างสี่เหลี่ยมผืนผ้าเพื่อตัดข้อความขึ้นบรรทัดใหม่ได้ ซึ่งอาจฟังดูขัดกับความรู้สึกเมื่อพิจารณาจากสมมติฐานเบื้องต้นที่ว่า CSS Shapes ช่วยให้เนื้อหาเว็บเป็นอิสระจากกล่องสี่เหลี่ยมธรรมดาๆ อาจเป็นไปได้ ฉันยังไม่พบ Use Case สำหรับ inset() ที่ไม่สามารถทำได้ด้วย Float และ Margin หรือด้วย polygon() แม้ว่า inset() จะมีนิพจน์ที่อ่านง่ายกว่าสำหรับรูปทรงสี่เหลี่ยมผืนผ้ามากกว่า polygon()
สัญกรณ์แบบเต็มสำหรับฟังก์ชันรูปร่างที่แทรกคือ inset(top right bottom left border-radius) อาร์กิวเมนต์ตำแหน่ง 4 รายการแรกคือออฟเซ็ตที่อยู่ด้านในจากขอบขององค์ประกอบ อาร์กิวเมนต์สุดท้ายคือรัศมีเส้นขอบสำหรับรูปร่างสี่เหลี่ยมผืนผ้า ซึ่งคุณจะเลือกไม่ระบุข้อมูลนี้ก็ได้ โดยจะเป็นไปตามสัญกรณ์ชวเลข border-radius ที่คุณใช้อยู่แล้วใน CSS
.element{
shape-outside: inset(100px 100px 100px 100px);
/* yields a rectangular shape which is 100px inset on all sides */
float: left;
}
การสร้างรูปร่างจากกล่องอ้างอิง
หากไม่ได้ระบุฟังก์ชันรูปร่างให้กับพร็อพเพอร์ตี้ shape-outside คุณสามารถอนุญาตให้เบราว์เซอร์ดึงรูปร่างจากกล่องอ้างอิงขององค์ประกอบได้ ช่องอ้างอิงเริ่มต้นคือ margin-box จนถึงตอนนี้ก็ยังไม่มีอะไรแปลกใหม่ นั่นคือวิธีการทำงานของ Float อยู่แล้ว แต่การใช้เทคนิคนี้จะช่วยให้คุณนำรูปทรงเรขาคณิตขององค์ประกอบมาใช้ซ้ำได้ มาดูพร็อพเพอร์ตี้ border-radius กัน
หากใช้เพื่อปัดมุมขององค์ประกอบที่ลอยอยู่ คุณจะได้รับเอฟเฟกต์การตัดคลิป แต่พื้นที่ลอยจะยังคงเป็นสี่เหลี่ยมผืนผ้า เพิ่ม shape-outside: border-box เพื่อพันรอบเส้นโครงร่างที่สร้างโดย border-radius
.element{
border-radius: 50%;
shape-outside: border-box;
float: left;
}
แน่นอนว่าคุณสามารถใช้ช่องอ้างอิงทั้งหมดในลักษณะนี้ได้ นี่คืออีกวิธีหนึ่งในการใช้รูปร่างที่ได้มา - การดึงข้อความอ้างอิงแบบออฟเซ็ต
คุณสามารถสร้างเอฟเฟกต์ข้อความดึงดูดสายตาแบบเยื้องได้โดยใช้เฉพาะพร็อพเพอร์ตี้ float และ margin แต่คุณต้องวางองค์ประกอบคำพูดในโครงสร้าง HTML ณ จุดที่ต้องการให้แสดงผล
วิธีสร้างเอฟเฟกต์ข้อความดึงดูดสายตาแบบเยื้องที่มีความยืดหยุ่นมากขึ้นมีดังนี้
.pull-quote{
shape-outside: content-box;
margin-top: 200px;
float: left;
}
เราตั้งค่ากล่องอ้างอิง content-box สำหรับระบบพิกัดของรูปร่างอย่างชัดเจน ในกรณีนี้ ปริมาณเนื้อหาในข้อความดึงดูดความสนใจจะเป็นตัวกำหนดรูปร่างที่เนื้อหาภายนอกจะตัดขึ้นบรรทัดใหม่ พร็อพเพอร์ตี้ margin-top ใช้ที่นี่เพื่อจัดตำแหน่ง (ออฟเซ็ต) คำพูดที่ดึงมา โดยไม่คำนึงถึงตำแหน่งในโครงสร้าง HTML
ขอบรูปร่าง
คุณจะสังเกตเห็นว่าการตัดข้อความรอบรูปร่างอาจทำให้ข้อความอยู่ชิดกับองค์ประกอบมากเกินไป คุณเพิ่มระยะห่างรอบรูปร่างได้ด้วยพร็อพเพอร์ตี้ shape-margin
.element{
shape-outside: circle(40%);
shape-margin: 1em;
float: left;
}
ผลลัพธ์จะคล้ายกับสิ่งที่คุณคุ้นเคยจากการใช้พร็อพเพอร์ตี้ margin ปกติ แต่ shape-margin จะส่งผลต่อพื้นที่รอบๆ ค่า shape-outside เท่านั้น ระบบจะเพิ่มระยะห่างรอบรูปร่างก็ต่อเมื่อมีพื้นที่ว่างในระบบพิกัดเท่านั้น ด้วยเหตุนี้ ในตัวอย่างด้านบนจึงตั้งค่ารัศมีวงกลมเป็น 40% ไม่ใช่ 50% หากตั้งค่ารัศมีเป็น 50% วงกลมจะใช้พื้นที่ทั้งหมดในระบบพิกัด ทำให้ไม่มีพื้นที่สำหรับผลลัพธ์ของ shape-margin โปรดทราบว่ารูปร่างจะถูกจำกัดให้อยู่ใน margin-box ขององค์ประกอบ (องค์ประกอบบวกกับ margin โดยรอบ) หากรูปร่างมีขนาดใหญ่กว่าและล้นออกมา รูปร่างจะถูกตัดให้พอดีกับ margin-box และคุณจะได้รูปร่างสี่เหลี่ยมผืนผ้า
โปรดทราบว่า shape-margin ยอมรับเฉพาะค่าบวกค่าเดียวเท่านั้น ไม่มีสัญกรณ์แบบยาว ว่าแต่ shape-margin-top สำหรับวงกลมคืออะไร
การสร้างภาพเคลื่อนไหวของรูปร่าง
คุณสามารถผสมผสานรูปร่าง CSS กับฟีเจอร์ CSS อื่นๆ ได้มากมาย เช่น การเปลี่ยนภาพและภาพเคลื่อนไหว อย่างไรก็ตาม เราต้องเน้นย้ำว่าผู้ใช้จะรู้สึกรำคาญมากเมื่อเลย์เอาต์ข้อความเปลี่ยนไปขณะที่กำลังอ่าน โปรดพิจารณาประสบการณ์การใช้งานอย่างรอบคอบหากคุณตัดสินใจที่จะใช้รูปร่างแบบเคลื่อนไหว
คุณสามารถทำให้รัศมีและจุดศูนย์กลางของรูปร่าง circle() และ ellipse() เคลื่อนไหวได้ ตราบใดที่มีการกำหนดค่าที่เบราว์เซอร์สามารถประมาณค่าในช่วงได้ การเปลี่ยนจาก circle(30%) เป็น circle(50%) เป็นไปได้ อย่างไรก็ตาม การสร้างภาพเคลื่อนไหวระหว่าง circle(closest-side) ถึง circle(farthest-side) จะทำให้เบราว์เซอร์ทำงานช้าลง
.element{
shape-outside: circle(30%);
transition: shape-outside 1s;
float: left;
}
.element:hover{
shape-outside: circle(50%);
}
คุณสามารถสร้างเอฟเฟกต์ที่น่าสนใจมากขึ้นได้เมื่อสร้างภาพเคลื่อนไหวของรูปร่าง polygon() โดยมีข้อควรทราบที่สำคัญคือรูปหลายเหลี่ยมต้องมีจำนวนจุดยอดเท่ากันระหว่างสถานะภาพเคลื่อนไหวทั้ง 2 สถานะ เบราว์เซอร์จะประมาณค่าในช่วงไม่ได้หากคุณเพิ่มหรือนำจุดยอดออก
เคล็ดลับหนึ่งคือการเพิ่มจำนวนจุดยอดสูงสุดที่คุณต้องการ และจัดตำแหน่งให้รวมกันเป็นกลุ่มในสถานะภาพเคลื่อนไหวที่คุณต้องการให้ขอบของรูปร่างดูน้อยลง
.element{
/* four vertices (looks like rectangle) */
shape-outside: polygon(0 0, 100% 0, 100% 100%, 0 100%);
transition: shape-outside 1s;
}
.element:hover{
/* four vertices, but second and third overlap (looks like triangle) */
shape-outside: polygon(0 0, 100% 50%, 100% 50%, 0 100%);
}
การตัดข้อความภายในรูปร่าง
ฉบับร่างแรกของข้อกำหนด CSS Shapes มีพร็อพเพอร์ตี้ shape-inside ซึ่งช่วยให้คุณตัดเนื้อหาภายในรูปร่างได้ และยังมีการติดตั้งใช้งานใน Chrome และ Webkit อยู่ระยะหนึ่งด้วย แต่การรวมเนื้อหาที่วางตำแหน่งตามใจชอบไว้ในเส้นทางที่กำหนดเองนั้นต้องใช้ความพยายามและการวิจัยมากกว่ามากเพื่อให้ครอบคลุมสถานการณ์ที่เป็นไปได้ทั้งหมดและหลีกเลี่ยงข้อบกพร่อง ด้วยเหตุนี้ พร็อพเพอร์ตี้ shape-inside จึงถูกเลื่อนไปเป็น CSS Shapes ระดับ 2 และการใช้งานพร็อพเพอร์ตี้ดังกล่าวถูกถอนออก
อย่างไรก็ตาม คุณยังคงสามารถตัดเนื้อหาภายในรูปร่างที่กำหนดเองได้โดยใช้ความพยายามและการปรับเปลี่ยนเล็กน้อย วิธีแก้ปัญหาคือการใช้องค์ประกอบแบบลอย 2 รายการที่มี shape-outside ซึ่งวางอยู่ที่ด้านตรงข้ามของคอนเทนเนอร์ ข้อเสียคือคุณต้องใช้องค์ประกอบว่าง 1 หรือ 2 รายการที่ไม่มีความหมายเชิงความหมาย แต่ทำหน้าที่เป็นตัวค้ำเพื่อสร้างภาพลวงตาของรูปร่างภายใน
<div>
<div class='left-shape'></div>
<div class='right-shape'></div>
Lorem ipsum...
</div>
ตำแหน่งขององค์ประกอบสตรัท .left-shape และ .right-shape ที่ด้านบนของคอนเทนเนอร์มีความสำคัญเนื่องจากจะลอยไปทางซ้ายและขวาเพื่อขนาบข้างเนื้อหา
.left-shape{
shape-outside: polygon(0 0, ...);
float: left;
width: 50%;
height: 100%;
}
.right-shape{
shape-outside: polygon(50% 0, ...);
float: right;
width: 50%;
height: 100%;
}
การจัดรูปแบบนี้ทำให้สตรัทแบบลอยทั้ง 2 ตัวใช้พื้นที่ทั้งหมดภายในองค์ประกอบ แต่พร็อพเพอร์ตี้ shape-outside จะแบ่งพื้นที่สำหรับเนื้อหาที่เหลือ
หากเบราว์เซอร์ไม่รองรับรูปร่าง CSS จะทำให้เกิดผลลัพธ์ที่ไม่น่าดูโดยการดันเนื้อหาทั้งหมดลงไปด้านล่าง ดังนั้นจึงควรใช้ฟีเจอร์นี้ในลักษณะที่ปรับปรุงอย่างต่อเนื่อง
ในตัวอย่างภาพเคลื่อนไหวของรูปร่างก่อนหน้านี้ คุณจะสังเกตเห็นว่าการเลื่อนข้อความไปมาอาจสร้างความรำคาญได้ กรณีการใช้งานบางกรณีอาจไม่จำเป็นต้องใช้รูปร่างแบบเคลื่อนไหว แต่คุณสามารถทำให้พร็อพเพอร์ตี้อื่นๆ เคลื่อนไหวได้ ซึ่งจะโต้ตอบกับรูปร่าง CSS เพื่อเพิ่มเอฟเฟกต์ในจุดที่เหมาะสม
ในการสาธิต CSS Shapes ของ Alice in Wonderland เราใช้ตำแหน่งการเลื่อนเพื่อเปลี่ยนระยะขอบด้านบนของเนื้อหา ข้อความถูกบีบให้อยู่ระหว่างองค์ประกอบแบบลอย 2 รายการ เมื่อเลื่อนลงมา ก็จะต้องจัดวางเลย์เอาต์ใหม่ตาม shape-outside ขององค์ประกอบที่ลอยอยู่ 2 รายการ ซึ่งทำให้รู้สึกว่าข้อความกำลังดำดิ่งลงไปในโพรงกระต่ายและช่วยเพิ่มประสบการณ์การเล่าเรื่อง อาจจะเปิดเผยโดยไม่จำเป็น? อาจจะได้ แต่ก็ดูเท่ดีนะ
เนื่องจากเลย์เอาต์ข้อความดำเนินการโดยเบราว์เซอร์โดยตรง ประสิทธิภาพจึงดีกว่าการใช้โซลูชัน JavaScript แต่การเปลี่ยน margin-top ในการเลื่อนจะทริกเกอร์เหตุการณ์การจัดเลย์เอาต์ใหม่และการวาดจำนวนมาก ซึ่งอาจลดประสิทธิภาพลงอย่างเห็นได้ชัด โปรดใช้ด้วยความระมัดระวัง อย่างไรก็ตาม การใช้รูปร่าง CSS โดยไม่ทำให้เคลื่อนไหวจะไม่ส่งผลต่อประสิทธิภาพที่สังเกตเห็นได้
การเพิ่มประสิทธิภาพแบบต่อเนื่อง
เริ่มต้นด้วยการสมมติว่าเบราว์เซอร์ไม่รองรับรูปร่าง CSS และสร้างขึ้นจากสมมติฐานนั้นเมื่อคุณตรวจพบฟีเจอร์ Modernizr เป็นโซลูชันที่ดีในการตรวจหาฟีเจอร์ และมีการทดสอบ CSS Shapes ในส่วน "Non-core detects"
เบราว์เซอร์บางตัวมีการตรวจหาฟีเจอร์ใน CSS ผ่านกฎ @supports โดยไม่ต้องใช้ไลบรารีภายนอก Google Chrome ซึ่งรองรับ CSS Shapes ด้วยจะเข้าใจกฎ @supports วิธีใช้เพื่อการเพิ่มประสิทธิภาพแบบต่อเนื่องมีดังนี้
.element{
/* styles for all browsers */
}
@supports (shape-outside: circle(50%)){
/* styles only for browsers which support CSS Shapes */
.element{
shape-outside: circle(50%);
}
}
Lea Verou ได้เขียนข้อมูลเพิ่มเติมเกี่ยวกับวิธีใช้กฎ CSS @supports
การแก้ความกำกวมจากการยกเว้น CSS
สิ่งที่เรารู้จักกันในปัจจุบันในชื่อ CSS Shapes เคยเรียกว่า CSS Exclusions and Shapes ในช่วงแรกๆ ของข้อกำหนด การเปลี่ยนชื่ออาจดูเหมือนเป็นความแตกต่างเล็กน้อย แต่จริงๆ แล้วมีความสำคัญมาก CSS Exclusions ซึ่งปัจจุบันเป็นข้อกำหนดแยกต่างหาก ช่วยให้สามารถตัดข้อความรอบองค์ประกอบที่วางตำแหน่งตามใจชอบได้โดยไม่ต้องใช้พร็อพเพอร์ตี้ Float ลองนึกภาพการตัดเนื้อหารอบองค์ประกอบที่วางตำแหน่งแบบสัมบูรณ์ ซึ่งเป็นกรณีการใช้งานสำหรับการยกเว้น CSS รูปร่าง CSS จะกำหนดเส้นทางที่เนื้อหาจะตัดขึ้นบรรทัดใหม่
ดังนั้นรูปร่างและการยกเว้นจึงไม่ใช่สิ่งเดียวกัน แต่จะช่วยเสริมกันและกัน ปัจจุบัน CSS Shapes พร้อมใช้งานในเบราว์เซอร์แล้ว แต่ CSS Exclusions ยังไม่ได้นำมาใช้กับการโต้ตอบกับรูปร่าง
เครื่องมือสำหรับการทำงานกับรูปร่าง CSS
คุณสามารถสร้างเส้นทางในเครื่องมือเขียนรูปภาพแบบคลาสสิกได้ แต่ในขณะที่เขียนบทความนี้ ไม่มีเครื่องมือใดที่ส่งออกไวยากรณ์ที่จำเป็นสำหรับค่ารูปร่าง CSS และถึงแม้จะทำได้ การทำงานแบบนั้นก็ไม่ค่อยมีประสิทธิภาพเท่าไรนัก
รูปร่าง CSS มีไว้เพื่อใช้ในเบราว์เซอร์ ซึ่งจะตอบสนองต่อองค์ประกอบอื่นๆ ในหน้าเว็บ การแสดงภาพผลลัพธ์ของการแก้ไขรูปร่างในเนื้อหาที่อยู่รอบๆ จะมีประโยชน์มาก มีเครื่องมือบางอย่างที่จะช่วยคุณในเวิร์กโฟลว์นี้ ได้แก่
Brackets: ส่วนขยาย CSS Shapes Editor สำหรับ Brackets ใช้โหมดแสดงตัวอย่างแบบเรียลไทม์ของตัวแก้ไขโค้ดเพื่อวางซ้อนเครื่องมือแก้ไขแบบอินเทอร์แอกทีฟสำหรับการแก้ไขค่ารูปร่าง
Google Chrome: ส่วนขยาย CSS Shapes Editor สำหรับ Google Chrome จะเพิ่มเครื่องมือสำหรับนักพัฒนาซอฟต์แวร์ของเบราว์เซอร์ด้วยการควบคุมเพื่อสร้างและแก้ไขรูปร่าง ซึ่งจะวางเครื่องมือแก้ไขแบบอินเทอร์แอกทีฟไว้ด้านบนขององค์ประกอบที่เลือก
เครื่องมือตรวจสอบใน Google Chrome มีการรองรับในตัวสำหรับการไฮไลต์รูปร่าง วางเมาส์เหนือองค์ประกอบที่มีพร็อพเพอร์ตี้ shape-outside แล้วองค์ประกอบจะสว่างขึ้นเพื่อแสดงรูปร่าง
รูปร่างจากรูปภาพ: หากคุณต้องการสร้างรูปภาพและให้เบราว์เซอร์ดึงรูปร่างจากรูปภาพ Rebecca Hauck ได้เขียนบทแนะนำสำหรับ Photoshop ไว้เป็นอย่างดี
Polyfill: Google Chrome เป็นเบราว์เซอร์หลักรายแรกที่จัดส่ง CSS Shapes ฟีเจอร์นี้จะรองรับ iOS 8 และ Safari 8 ของ Apple ในเร็วๆ นี้ ผู้ให้บริการเบราว์เซอร์รายอื่นๆ อาจพิจารณาใช้ในอนาคต ในระหว่างนี้ คุณสามารถใช้ CSS Shapes polyfill เพื่อให้การรองรับขั้นพื้นฐานได้
บทสรุป
ในเว็บที่เนื้อหาส่วนใหญ่ติดอยู่ในกล่องธรรมดา รูปทรง CSS จะช่วยสร้างเลย์เอาต์ที่สื่อความหมายได้ ซึ่งช่วยลดช่องว่างด้านความแม่นยำระหว่างการออกแบบเว็บและการออกแบบสิ่งพิมพ์ แน่นอนว่าอาจมีการใช้รูปทรงในทางที่ผิดและสร้างความรำคาญได้ แต่เมื่อนำมาใช้ด้วยรสนิยมและการพิจารณาที่ดี รูปร่างจะช่วยปรับปรุงการนำเสนอเนื้อหาและดึงดูดความสนใจของผู้ใช้ในแบบที่ไม่เหมือนใครได้
เราขอฝากคอลเล็กชันผลงานของผู้อื่น ซึ่งส่วนใหญ่มาจากสื่อสิ่งพิมพ์ที่แสดงให้เห็นถึงการใช้เลย์เอาต์ที่ไม่ใช่สี่เหลี่ยมผืนผ้าอย่างน่าสนใจ เราหวังว่าข้อมูลนี้จะช่วยสร้างแรงบันดาลใจให้คุณลองใช้รูปร่าง CSS และทดลองใช้แนวคิดการออกแบบใหม่ๆ
ขอขอบคุณ Pearl Chen, Alan Stearns และ Zoltan Horvath ที่ช่วยตรวจสอบบทความนี้และให้ข้อมูลเชิงลึกที่มีคุณค่า