ปรับปรุงการจัดรูปแบบเริ่มต้นของโหมดมืดด้วยพร็อพเพอร์ตี้ CSS สำหรับรูปแบบสีและเมตาแท็กที่เกี่ยวข้อง

พร็อพเพอร์ตี้ color-scheme CSS และแท็ก Meta ที่เกี่ยวข้อง ช่วยให้นักพัฒนาซอฟต์แวร์เลือกให้หน้าเว็บใช้ค่าเริ่มต้นเฉพาะธีมของสไตล์ชีต User Agent ได้

ฉากหลัง

prefers-color-schemeฟีเจอร์สื่อการตั้งค่าของผู้ใช้

ฟีเจอร์สื่อค่ากำหนดของผู้ใช้ prefers-color-scheme ช่วยให้นักพัฒนาแอปควบคุมลักษณะที่ปรากฏของหน้าเว็บได้อย่างเต็มที่ หากคุณไม่คุ้นเคยกับเรื่องนี้ โปรดอ่านบทความ prefers-color-scheme: Hello darkness, my old friend ที่ฉันได้บันทึกทุกสิ่งที่รู้เกี่ยวกับการสร้างประสบการณ์โหมดมืดที่ยอดเยี่ยม

จิ๊กซอว์ชิ้นหนึ่งที่กล่าวถึงเพียงสั้นๆ ในบทความคือพร็อพเพอร์ตี้ CSS color-scheme และแท็ก Meta ที่มีชื่อเดียวกัน ทั้ง 2 อย่างนี้จะช่วยให้คุณในฐานะนักพัฒนาแอปทำงานได้ง่ายขึ้น โดยให้คุณเลือกใช้ค่าเริ่มต้นเฉพาะธีมของชีตสไตล์ User Agent เช่น ตัวควบคุมแบบฟอร์ม แถบเลื่อน รวมถึงสีของระบบ CSS ในขณะเดียวกัน ฟีเจอร์นี้จะป้องกันไม่ให้เบราว์เซอร์ใช้การเปลี่ยนรูปแบบใดๆ ด้วยตัวเอง

การสนับสนุนเบราว์เซอร์

prefers-color-scheme

Browser Support

  • Chrome: 76.
  • Edge: 79.
  • Firefox: 67.
  • Safari: 12.1.

Source

color-scheme

Browser Support

  • Chrome: 81.
  • Edge: 81.
  • Firefox: 96.
  • Safari: 13.

Source

สไตล์ชีต User Agent

ก่อนจะพูดต่อ ขออธิบายสั้นๆ ว่าสไตล์ชีต User Agent คืออะไร ส่วนใหญ่แล้ว คุณอาจคิดว่าคำว่า User Agent (UA) เป็นวิธีที่ดูดีในการพูดถึงเบราว์เซอร์ สไตล์ชีตของ UA จะกำหนดรูปลักษณ์เริ่มต้นของหน้าเว็บ ตามชื่อที่ระบุไว้ สไตล์ชีต UA คือสิ่งที่ขึ้นอยู่กับ UA ที่เกี่ยวข้อง คุณสามารถดูสไตล์ชีต UA ของ Chrome (และ Chromium) และเปรียบเทียบกับของ Firefox หรือ Safari (และ WebKit) โดยปกติแล้ว ชีตสไตล์ของ UA จะเห็นพ้องในเรื่องส่วนใหญ่ เช่น ทั้งหมดจะทำให้ลิงก์เป็นสีน้ำเงิน ข้อความทั่วไปเป็นสีดำ และสีพื้นหลังเป็นสีขาว แต่ก็มีข้อแตกต่างที่สำคัญ (และบางครั้งก็น่ารำคาญ) ด้วย เช่น วิธีจัดรูปแบบตัวควบคุมแบบฟอร์ม

ดูรายละเอียดเพิ่มเติมเกี่ยวกับ สไตล์ชีต UA ของ WebKit และสิ่งที่สไตล์ชีตทำเกี่ยวกับโหมดมืด (ค้นหาข้อความแบบเต็มสำหรับ "dark" ในสไตล์ชีต) ค่าเริ่มต้นที่จัดทำโดยชีตสไตล์จะเปลี่ยนแปลงตามว่าเปิดหรือปิดโหมดมืด เพื่อแสดงให้เห็นภาพ ต่อไปนี้คือกฎ CSS ดังกล่าวโดยใช้ :matches คลาสเสมือนและตัวแปรภายในของ WebKit เช่น -apple-system-control-background รวมถึงคำสั่งตัวประมวลผลล่วงหน้าภายในของ WebKit #if defined

input,
input:matches([type="password"], [type="search"]) {
  -webkit-appearance: textfield;
  #if defined(HAVE_OS_DARK_MODE_SUPPORT) &&
      HAVE_OS_DARK_MODE_SUPPORT
    color: text;
    background-color: -apple-system-control-background;
  #else
    background-color: white;
  #endif
  /* snip */
}

คุณจะเห็นค่าที่ไม่เป็นไปตามมาตรฐานสำหรับพร็อพเพอร์ตี้ color และ background-color ด้านบน ทั้ง text และ -apple-system-control-background ไม่ใช่สี CSS ที่ถูกต้อง ซึ่งเป็นสีเชิงความหมายภายในของ WebKit

ปรากฏว่า CSS มีการกำหนดสีของระบบเชิงความหมายที่เป็นมาตรฐาน โดยระบุไว้ใน โมดูลสี CSS ระดับ 4 เช่น Canvas (อย่าสับสนกับแท็ก <canvas>) ใช้สำหรับพื้นหลังของเนื้อหาหรือเอกสารของแอปพลิเคชัน ส่วน CanvasText ใช้สำหรับข้อความในเนื้อหาหรือเอกสารของแอปพลิเคชัน ทั้ง 2 อย่างนี้ควรใช้ร่วมกันและไม่ควรใช้แยกกัน

สไตล์ชีตของ UA สามารถใช้สีของระบบที่เป็นกรรมสิทธิ์ของตนเองหรือสีของระบบเชิงความหมายที่ได้มาตรฐาน เพื่อกำหนดวิธีที่ควรแสดงผลองค์ประกอบ HTML โดยค่าเริ่มต้น หากระบบปฏิบัติการตั้งค่าเป็นโหมดมืดหรือใช้ธีมมืด CanvasText (หรือ text) จะตั้งค่าเป็นสีขาวแบบมีเงื่อนไข และ Canvas (หรือ -apple-system-control-background) จะตั้งค่าเป็นสีดำ จากนั้นชีตสไตล์ UA จะกำหนด CSS ต่อไปนี้เพียงครั้งเดียว และครอบคลุมทั้งโหมดสว่างและโหมดมืด

/**
  Not actual UA stylesheet code.
  For illustrative purposes only.
*/
body {
  color: CanvasText;
  background-color: Canvas
}

พร็อพเพอร์ตี้ color-scheme CSS

ข้อกําหนดโมดูลการปรับสี CSS ระดับ 1 แนะนํารูปแบบและการควบคุม การปรับสีอัตโนมัติโดย User Agent โดยมีวัตถุประสงค์เพื่อจัดการค่ากําหนดของผู้ใช้ เช่น โหมดมืด การปรับคอนทราสต์ หรือรูปแบบสีที่ต้องการ

พร็อพเพอร์ตี้ color-scheme ที่กำหนดไว้ในนั้นจะช่วยให้องค์ประกอบระบุได้ว่าต้องการให้แสดงด้วยรูปแบบสีใด ค่าเหล่านี้จะได้รับการเจรจาตามค่ากําหนดของผู้ใช้ ซึ่งส่งผลให้มีการเลือกรูปแบบสี ที่มีผลต่อสิ่งต่างๆ ในอินเทอร์เฟซผู้ใช้ (UI) เช่น สีเริ่มต้นของตัวควบคุมแบบฟอร์ม และแถบเลื่อน รวมถึงค่าที่ใช้ของสีระบบ CSS ปัจจุบันระบบรองรับค่าต่อไปนี้

  • normal ระบุว่าองค์ประกอบไม่ทราบรูปแบบสีเลย ดังนั้นควรแสดงองค์ประกอบด้วยรูปแบบสีเริ่มต้นของเบราว์เซอร์

  • [ light | dark ]+ ระบุว่าองค์ประกอบทราบและจัดการรูปแบบสีที่ระบุได้ และแสดงถึงลำดับการกำหนดลักษณะระหว่างรูปแบบสีเหล่านั้น

ในรายการนี้ light หมายถึงรูปแบบสีอ่อน ที่มีสีพื้นหลังอ่อนและสีพื้นหน้าเข้ม ส่วน dark หมายถึงรูปแบบสีตรงกันข้าม ที่มีสีพื้นหลังเข้มและสีพื้นหน้าอ่อน

สําหรับองค์ประกอบทั้งหมด การแสดงผลด้วยรูปแบบสีควรทําให้สีที่ใช้ ใน UI ทั้งหมดที่เบราว์เซอร์มีให้สําหรับองค์ประกอบตรงกับเจตนาของรูปแบบสี ตัวอย่างเช่น แถบเลื่อน เส้นใต้ตรวจตัวสะกด ตัวควบคุมแบบฟอร์ม ฯลฯ

ในองค์ประกอบ :root การแสดงผลด้วยรูปแบบสี ต้องส่งผลต่อสีพื้นผิวของ Canvas (นั่นคือสีพื้นหลังส่วนกลาง) ค่าเริ่มต้นของพร็อพเพอร์ตี้ color และค่าที่ใช้ของสีระบบ และควรส่งผลต่อแถบเลื่อนของวิวพอร์ตด้วย

/*
  The page supports both dark and light color schemes,
  and the page author prefers dark.
*/
:root {
  color-scheme: dark light;
}

เมตาแท็ก color-scheme

การใช้color-schemeพร็อพเพอร์ตี้ CSS ต้องดาวน์โหลด CSS ก่อน (หากมีการอ้างอิงผ่าน <link rel="stylesheet">) และต้องแยกวิเคราะห์ หากต้องการช่วย User Agent ในการแสดงพื้นหลังของหน้าเว็บด้วยรูปแบบสีที่ต้องการทันที คุณสามารถระบุค่า color-scheme ในองค์ประกอบ <meta name="color-scheme"> ได้ด้วย

<!--
  The page supports both dark and light color schemes,
  and the page author prefers dark.
-->
<meta name="color-scheme" content="dark light">

การรวม color-scheme และ prefers-color-scheme

เนื่องจากทั้งเมตาแท็กและพร็อพเพอร์ตี้ CSS (หากใช้กับองค์ประกอบ :root) จะส่งผลให้เกิดลักษณะการทำงานเดียวกันในท้ายที่สุด ฉันจึงขอแนะนำให้ระบุรูปแบบสี ผ่านเมตาแท็กเสมอ เพื่อให้เบราว์เซอร์ปรับใช้รูปแบบที่ต้องการได้เร็วขึ้น

แม้ว่าหน้าเว็บพื้นฐานที่แน่นอนจะไม่จำเป็นต้องมีกฎ CSS เพิ่มเติม แต่ในกรณีทั่วไป คุณควรใช้ color-scheme ร่วมกับ prefers-color-scheme เสมอ ตัวอย่างเช่น สี CSS -webkit-link ของ WebKit ที่ใช้โดย WebKit และ Chrome สำหรับสีน้ำเงินของลิงก์คลาสสิก rgb(0,0,238) มีอัตราส่วนคอนทราสต์ไม่เพียงพอที่ 2.23:1 บนพื้นหลังสีดำ และไม่เป็นไปตาม ทั้งข้อกำหนด WCAG AA และ WCAG AAA ข้อกำหนด

ฉันได้เปิดข้อบกพร่องสำหรับ Chrome, WebKit และ Firefox รวมถึงปัญหาเมตาในมาตรฐาน HTML เพื่อแก้ไขปัญหานี้

Interplay with prefers-color-scheme

การทำงานร่วมกันของพร็อพเพอร์ตี้ color-scheme CSS และแท็ก Meta ที่เกี่ยวข้อง กับฟีเจอร์สื่อค่ากำหนดของผู้ใช้ prefers-color-scheme อาจดูสับสนในตอนแรก ซึ่งทั้ง 2 อย่างนี้ทำงานร่วมกันได้ดีมาก สิ่งสำคัญที่สุดที่ต้องทำความเข้าใจคือ color-scheme จะกำหนดลักษณะเริ่มต้นโดยเฉพาะ ในขณะที่ prefers-color-scheme จะกำหนดลักษณะที่จัดรูปแบบได้ เพื่อให้เข้าใจได้ชัดเจนยิ่งขึ้น ให้พิจารณาหน้าเว็บต่อไปนี้

<head>
  <meta name="color-scheme" content="dark light">
  <style>
    fieldset {
      background-color: gainsboro;
    }
    @media (prefers-color-scheme: dark) {
      fieldset {
        background-color: darkslategray;
      }
    }
  </style>
</head>
<body>
  <p>
    Lorem ipsum dolor sit amet, legere ancillae ne vis.
  </p>
  <form>
    <fieldset>
      <legend>Lorem ipsum</legend>
      <button type="button">Lorem ipsum</button>
    </fieldset>
  </form>
</body>

โค้ด CSS แบบอินไลน์ในหน้าเว็บ ตั้งค่า background-color ขององค์ประกอบ <fieldset> เป็น gainsboro ในกรณีทั่วไป และเป็น darkslategray หากผู้ใช้ต้องการใช้รูปแบบสี dark ตามฟีเจอร์สื่อค่ากำหนดของผู้ใช้ prefers-color-scheme

องค์ประกอบ <meta name="color-scheme" content="dark light"> หน้าเว็บจะบอกเบราว์เซอร์ว่ารองรับทั้งธีมมืดและธีมสว่าง โดยมีค่ากำหนดเป็นธีมมืด

ทั้งหน้าเว็บจะปรากฏเป็นสีอ่อนบนพื้นสีเข้มหรือในทางกลับกันตามสไตล์ชีตของ User Agent ทั้งนี้ขึ้นอยู่กับการตั้งค่าระบบปฏิบัติการเป็นโหมดมืดหรือโหมดสว่าง ไม่มี CSS เพิ่มเติมที่นักพัฒนาซอฟต์แวร์จัดเตรียมไว้ให้เพื่อเปลี่ยนข้อความย่อหน้า หรือสีพื้นหลังของหน้าเว็บ

สังเกตว่า <fieldset> ขององค์ประกอบ background-color เปลี่ยนแปลงอย่างไร โดยขึ้นอยู่กับว่าเปิดใช้โหมดมืดหรือไม่ ตามกฎ ในสไตล์ชีตแบบอินไลน์ที่นักพัฒนาซอฟต์แวร์ระบุไว้ในหน้า ซึ่งอาจเป็น gainsboro หรือ darkslategray

หน้าเว็บในโหมดสว่าง
โหมดสว่าง: รูปแบบที่นักพัฒนาแอปและ User Agent ระบุ ข้อความจะเป็นสีดำและพื้นหลังจะเป็นสีขาวตามสไตล์ชีตของ User Agent background-color ขององค์ประกอบ <fieldset> คือ gainsboro ตามสไตล์ชีตของนักพัฒนาแอปที่แทรกในบรรทัด
หน้าเว็บในโหมดมืด
โหมดมืด: รูปแบบที่นักพัฒนาซอฟต์แวร์และ User Agent ระบุ ข้อความเป็นสีขาวและพื้นหลังเป็นสีดำตามสไตล์ชีตของ User Agent background-color ขององค์ประกอบ <fieldset> คือ darkslategray ตามสไตล์ชีตของนักพัฒนาแอปที่แทรกในบรรทัด

ลักษณะที่ปรากฏขององค์ประกอบ <button> จะควบคุมโดยสไตล์ชีตของ User Agent color ตั้งค่าเป็นสีของระบบ ButtonText และตั้งค่า background-color และ border-color ทั้ง 4 รายการเป็นสีของระบบ ButtonFace

หน้าในโหมดสว่างที่ใช้พร็อพเพอร์ตี้ ButtonFace
โหมดสว่าง: ระบบจะตั้งค่า background-color และ border-color ต่างๆ เป็นสีของระบบ ButtonFace

ตอนนี้ให้สังเกตว่า border-color ขององค์ประกอบ <button> เปลี่ยนแปลงอย่างไร ค่าที่คำนวณแล้วสำหรับ border-top-color และ border-bottom-color จะเปลี่ยนจาก rgba(0, 0, 0, 0.847) (ดำ) เป็น rgba(255, 255, 255, 0.847) (ขาว) เนื่องจาก User Agent จะอัปเดต ButtonFace แบบไดนามิกตามรูปแบบสี เช่นเดียวกับ <button> ขององค์ประกอบ color ที่ตั้งค่าเป็นสีของระบบที่เกี่ยวข้อง ButtonText

แสดงว่าค่าสีที่คำนวณแล้วตรงกับ ButtonFace
โหมดสว่าง: ค่าที่คำนวณของ border-top-color และ border-bottom-color ซึ่งทั้ง 2 ค่าตั้งเป็น ButtonFace ในสไตล์ชีตของ User Agent ตอนนี้คือ rgba(0, 0, 0, 0.847)
แสดงว่าค่าสีที่คำนวณแล้วยังคงตรงกับ ButtonFace ขณะอยู่ในโหมดมืด
โหมดมืด: ค่าที่คำนวณของ border-top-color และ border-bottom-color ซึ่งทั้ง 2 ค่าตั้งเป็น ButtonFace ในชีตสไตล์ของ User Agent ตอนนี้เป็น rgba(255, 255, 255, 0.847) แล้ว

สาธิต

คุณดูผลลัพธ์ของ color-scheme ที่ใช้กับองค์ประกอบ HTML จำนวนมากได้ ในการสาธิตบน Glitch การสาธิตจงใจแสดงการละเมิด WCAG AA และ WCAG AAA โดยใช้สีลิงก์ที่กล่าวถึงในคำเตือนด้านบน

การสาธิตขณะอยู่ในโหมดสว่าง
การสาธิต สลับเป็น color-scheme: light
การสาธิตขณะอยู่ในโหมดมืด
การสาธิต สลับเป็น color-scheme: dark โปรดทราบว่า WCAG AA และ WCAG AAA การละเมิด ที่มีสีของลิงก์

การรับทราบ

color-scheme พร็อพเพอร์ตี้ CSS และเมตาแท็กที่เกี่ยวข้องได้รับการติดตั้งใช้งานโดย Rune Lillesveen นอกจากนี้ Rune ยังเป็นผู้ร่วมแก้ไขข้อกำหนดของโมดูลการปรับสี CSS ระดับ 1 ด้วย รูปภาพหลักโดย Philippe Leone ใน Unsplash