การรองรับเลเยอร์ระดับบนสุดในเครื่องมือสำหรับนักพัฒนาเว็บใน Chrome

Alina Varkki
Alina Varkki

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

บทความนี้อธิบายถึงองค์ประกอบของเลเยอร์บนสุด, วิธีที่เครื่องมือสำหรับนักพัฒนาเว็บช่วยให้เห็นภาพเนื้อหาของเลเยอร์บนสุดเพื่อทําความเข้าใจและแก้ไขข้อบกพร่องของโครงสร้าง DOM ที่มีองค์ประกอบของเลเยอร์ระดับบนสุด และวิธีใช้การรองรับเลเยอร์บนสุดของเครื่องมือสําหรับนักพัฒนาเว็บ

เลเยอร์บนสุดและองค์ประกอบของเลเยอร์บนสุดคืออะไร

จะเกิดอะไรขึ้นภายในบ้างเมื่อคุณเปิด <dialog> เป็นโมดัล 🤔

และใส่ลงไปในชั้นบนสุด เนื้อหาเลเยอร์ด้านบนจะแสดงทับเนื้อหาอื่นๆ ทั้งหมด ตัวอย่างเช่น กล่องโต้ตอบโมดัลต้องปรากฏที่ด้านบนของเนื้อหา DOM อื่นๆ ทั้งหมด เบราว์เซอร์จึงแสดงผลองค์ประกอบนี้ใน 'เลเยอร์บนสุด' โดยอัตโนมัติแทนการบังคับให้ผู้เขียนต่อสู้ด้วยดัชนี z ด้วยตนเอง องค์ประกอบเลเยอร์บนสุดจะปรากฏที่ด้านบนขององค์ประกอบหนึ่งแม้ว่าจะมีดัชนีลำดับ z สูงสุดก็ตาม

เลเยอร์บนสุดอาจอธิบายได้ว่าเป็น "เลเยอร์ซ้อนสูงสุด" เอกสารแต่ละฉบับมีวิวพอร์ตที่เชื่อมโยงกัน 1 ชั้น จึงเป็นเลเยอร์บนสุดชั้นเดียวด้วย องค์ประกอบหลายรายการสามารถอยู่ในเลเยอร์บนสุดพร้อมกันได้ เมื่อเกิดกรณีนี้ขึ้น แหล่งที่มาจะซ้อนกัน แถวสุดท้ายจะอยู่ด้านบน กล่าวคือ องค์ประกอบเลเยอร์บนสุดทั้งหมดจะอยู่ในกลุ่มสุดท้ายเข้า ออกก่อน (LIFO) ในเลเยอร์บนสุด

องค์ประกอบ <dialog> ไม่ใช่องค์ประกอบเดียวที่เบราว์เซอร์แสดงผลในเลเยอร์บนสุด ปัจจุบันองค์ประกอบของเลเยอร์ด้านบน ได้แก่ ป๊อปอัป กล่องโต้ตอบโมดัล และองค์ประกอบในโหมดเต็มหน้าจอ

ตรวจสอบการใช้งานกล่องโต้ตอบต่อไปนี้

<main>
  <button onclick="window.dialog.showModal();">Open Dialog</button>
</main>
<dialog id="dialog"></dialog>

นี่เป็นการสาธิตที่มีกล่องโต้ตอบ 2-3 กล่องโต้ตอบที่มีการใช้รูปแบบกับฉากหลัง (ฉากหลังอธิบายไว้ด้านล่าง)

ฉากหลังคืออะไร

โชคดีที่มีวิธีปรับแต่งเนื้อหาที่อยู่ใต้องค์ประกอบเลเยอร์บนสุด

ทุกองค์ประกอบในเลเยอร์บนสุดจะมีองค์ประกอบเทียม CSS ที่เรียกว่าฉากหลัง

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

เมื่อคุณสร้างโมดัลองค์ประกอบหลายรายการ เบราว์เซอร์จะวาดฉากหลังด้านล่างองค์ประกอบดังกล่าวไว้ด้านหน้าสุดและซ้อนทับองค์ประกอบแบบเต็มหน้าจออื่นๆ

วิธีการจัดรูปแบบฉากหลังมีดังนี้

/* The browser displays the backdrop only when the dialog.showModal() function opens the dialog.*/
dialog::backdrop {
    background: rgba(255,0,0,.25);
}

วิธีแสดงเฉพาะฉากหลังแรก

องค์ประกอบชั้นบนสุดทุกรายการจะมีฉากหลังที่เป็นของกองเลเยอร์บนสุด ฉากหลังเหล่านี้ออกแบบมาให้ซ้อนทับกัน ดังนั้นหากความทึบแสงของฉากหลังไม่เป็น 100% ระบบจะมองเห็นฉากหลังที่อยู่ด้านล่างได้

หากจำเป็นต้องมองเห็นเฉพาะฉากหลังแรกในกลุ่มเลเยอร์บนสุด คุณสามารถทำได้โดยการติดตามตัวระบุรายการในกลุ่มเลเยอร์บนสุด

หากองค์ประกอบที่เพิ่มไม่ใช่องค์ประกอบแรกในเลเยอร์บนสุด ฟังก์ชันที่เรียกใช้เมื่อใส่องค์ประกอบนั้นลงในเลเยอร์บนสุดจะใช้คลาส hiddenBackdrop กับ ::backdrop คลาสนี้จะถูกลบออกเมื่อนำองค์ประกอบออกจากเลเยอร์บนสุด

ดูโค้ดในการสาธิตตัวอย่างนี้

การออกแบบการรองรับเลเยอร์บนสุดในเครื่องมือสำหรับนักพัฒนาเว็บ

การรองรับเครื่องมือสำหรับนักพัฒนาเว็บสำหรับเลเยอร์บนสุดช่วยให้นักพัฒนาซอฟต์แวร์เข้าใจแนวคิดของเลเยอร์บนสุดและแสดงภาพการเปลี่ยนแปลงเนื้อหาของเลเยอร์บนสุด ฟีเจอร์เหล่านี้ช่วยให้นักพัฒนาแอประบุสิ่งต่อไปนี้ได้

  • องค์ประกอบในเลเยอร์บนสุดได้ทุกเมื่อและลำดับขององค์ประกอบ
  • องค์ประกอบที่ด้านบนของกลุ่ม ณ จุดใดก็ได้

นอกจากนี้ การรองรับเลเยอร์บนสุดของเครื่องมือสำหรับนักพัฒนาเว็บยังช่วยแสดงภาพตําแหน่งขององค์ประกอบเทียมของฉากหลังในกลุ่มเลเยอร์ชั้นบนสุดด้วย แม้จะไม่ใช่องค์ประกอบแบบต้นไม้ แต่ก็มีบทบาทสำคัญในวิธีการทำงานของเลเยอร์บนสุดและเป็นประโยชน์ต่อนักพัฒนาซอฟต์แวร์

ฟีเจอร์การสนับสนุนเลเยอร์บนสุดช่วยให้คุณสามารถทำสิ่งต่อไปนี้

  1. สังเกตได้ทุกเมื่อว่าองค์ประกอบใดอยู่ในกองซ้อนเลเยอร์บนสุด กลุ่มการแสดงเลเยอร์บนสุดจะเปลี่ยนแปลงแบบไดนามิกเมื่อมีการเพิ่มหรือนำองค์ประกอบออกจากเลเยอร์บนสุด
  2. ดูตำแหน่งองค์ประกอบในกลุ่มเลเยอร์บนสุด
  3. ข้ามจากองค์ประกอบของเลเยอร์บนสุดหรือองค์ประกอบเทียมของฉากหลังในต้นไม้ไปยังองค์ประกอบหรือองค์ประกอบเทียมของฉากหลังในคอนเทนเนอร์การแสดงเลเยอร์บนสุดและด้านหลัง

มาดูวิธีใช้ฟีเจอร์เหล่านี้กัน

คอนเทนเนอร์เลเยอร์บนสุด

เครื่องมือสำหรับนักพัฒนาเว็บจะเพิ่มคอนเทนเนอร์เลเยอร์บนสุดลงในแผนผังองค์ประกอบเพื่อช่วยให้คุณเห็นภาพองค์ประกอบเลเยอร์บนสุด อยู่หลังแท็กปิด </html>

คอนเทนเนอร์นี้ช่วยให้คุณสังเกตองค์ประกอบในกลุ่มเลเยอร์บนสุดได้ทุกเมื่อ คอนเทนเนอร์เลเยอร์บนสุดคือรายการลิงก์ไปยังองค์ประกอบเลเยอร์บนสุดและฉากหลัง กลุ่มการแสดงเลเยอร์บนสุดจะเปลี่ยนแปลงแบบไดนามิกเมื่อมีการเพิ่มหรือนำองค์ประกอบออกจากเลเยอร์บนสุด

หากต้องการค้นหาองค์ประกอบเลเยอร์บนสุดภายในแผนผังองค์ประกอบหรือคอนเทนเนอร์เลเยอร์บนสุด ให้คลิกลิงก์จากการแสดงองค์ประกอบเลเยอร์บนสุดในคอนเทนเนอร์เลเยอร์บนสุดไปยังองค์ประกอบเดียวกันในแผนผังองค์ประกอบและกลับ

หากต้องการข้ามจากองค์ประกอบคอนเทนเนอร์เลเยอร์บนสุดไปยังองค์ประกอบโครงสร้างเลเยอร์บนสุด ให้คลิกปุ่มแสดงข้างองค์ประกอบในคอนเทนเนอร์เลเยอร์บนสุด

ข้ามจากลิงก์คอนเทนเนอร์ของเลเยอร์บนสุดไปยังองค์ประกอบ

หากต้องการข้ามจากองค์ประกอบแผนผังเลเยอร์บนสุดไปยังลิงก์ในคอนเทนเนอร์เลเยอร์บนสุด ให้คลิกป้ายเลเยอร์บนสุดข้างองค์ประกอบนั้น

การข้ามจากองค์ประกอบไปยังลิงก์คอนเทนเนอร์ของเลเยอร์บนสุด

คุณสามารถปิดป้ายใดก็ได้ รวมถึงป้ายเลเยอร์ด้านบน หากต้องการปิดป้าย ให้คลิกขวาที่ป้ายใดก็ได้ เลือกการตั้งค่าป้าย แล้วลบเครื่องหมายถูกข้างๆ ป้ายที่คุณต้องการซ่อน

กำลังปิดป้าย

ลำดับองค์ประกอบในกลุ่มเลเยอร์บนสุด

คอนเทนเนอร์เลเยอร์บนสุดจะแสดงองค์ประกอบตามที่ปรากฏในกลุ่ม แต่เรียงกลับกัน ด้านบนขององค์ประกอบซ้อนคือองค์ประกอบสุดท้ายในรายการองค์ประกอบของคอนเทนเนอร์เลเยอร์บนสุด ซึ่งหมายความว่าองค์ประกอบสุดท้ายในรายการคอนเทนเนอร์ของเลเยอร์บนสุดคือองค์ประกอบที่คุณโต้ตอบด้วยในเอกสารได้ในปัจจุบัน

ป้ายข้างองค์ประกอบของต้นไม้จะระบุว่าองค์ประกอบนั้นๆ อยู่ในเลเยอร์บนสุดหรือไม่ และมีหมายเลขตำแหน่งขององค์ประกอบในกองซ้อนหรือไม่

ในภาพหน้าจอนี้ กลุ่มเลเยอร์บนสุดประกอบด้วย 2 องค์ประกอบ โดยองค์ประกอบที่ 2 จะอยู่ด้านบนของกลุ่ม หากคุณนำองค์ประกอบที่ 2 ออก องค์ประกอบแรกจะย้ายไปอยู่ด้านบน

ลำดับขององค์ประกอบในกอง

ฉากหลังในคอนเทนเนอร์ของเลเยอร์ระดับบนสุด

ดังที่กล่าวไว้ข้างต้น องค์ประกอบเลเยอร์ด้านบนทุกรายการจะมีองค์ประกอบเทียมของ CSS ที่เรียกว่าฉากหลัง คุณจัดรูปแบบองค์ประกอบนี้ได้ การตรวจสอบและดูการนำเสนอองค์ประกอบนี้จึงมีประโยชน์มาก

ในแผนผังองค์ประกอบ องค์ประกอบฉากหลังจะอยู่ก่อนแท็กปิดขององค์ประกอบที่มีองค์ประกอบฉากหลังอยู่ อย่างไรก็ตาม ลิงก์ฉากหลังจะปรากฏเหนือองค์ประกอบเลเยอร์ระดับบนสุดในคอนเทนเนอร์เลเยอร์บนสุด

ตำแหน่งของกองฉากหลัง

การเปลี่ยนแปลงของแผนผัง DOM

ElementsTreeElement ซึ่งเป็นคลาสที่มีหน้าที่สร้างและจัดการองค์ประกอบแผนผัง DOM แต่ละรายการในเครื่องมือสำหรับนักพัฒนาเว็บไม่เพียงพอต่อการใช้งานคอนเทนเนอร์เลเยอร์บนสุด

เราได้เพิ่มคลาสใหม่ที่สร้างโหนดองค์ประกอบแบบต้นไม้สำหรับ DevTools เพื่อแสดงคอนเทนเนอร์เลเยอร์บนสุดเป็นโหนดในแผนผัง ก่อนหน้านี้ คลาสที่มีหน้าที่สร้างแผนผังองค์ประกอบ DevTools เริ่มต้นทุก TreeElement ด้วย DOMNode ซึ่งเป็นคลาสที่มี backendNodeId และพร็อพเพอร์ตี้อื่นๆ เกี่ยวกับแบ็กเอนด์ ส่วน backendNodeId จะได้รับการกำหนดไว้ในแบ็กเอนด์

โหนดคอนเทนเนอร์ของเลเยอร์บนสุดที่มีรายการลิงก์ไปยังองค์ประกอบเลเยอร์บนสุด ซึ่งจำเป็นต้องทำหน้าที่เป็นโหนดองค์ประกอบต้นไม้ปกติ อย่างไรก็ตาม โหนดนี้ไม่ใช่โหนด DOM "จริง" และแบ็กเอนด์ไม่จําเป็นต้องสร้างโหนดคอนเทนเนอร์ของเลเยอร์บนสุด

ในการสร้างโหนดฟรอนท์เอนด์ที่แสดงถึงเลเยอร์บนสุด เราได้เพิ่มโหนดฟรอนท์เอนด์ประเภทใหม่ที่สร้างขึ้นโดยไม่มี DOMNode องค์ประกอบคอนเทนเนอร์เลเยอร์บนสุดนี้เป็นโหนดฟรอนท์เอนด์แรกที่ไม่มี DOMNode ซึ่งหมายความว่ามีอยู่เฉพาะในฟรอนท์เอนด์และแบ็กเอนด์จะ "ไม่ทราบ" เกี่ยวกับเรื่องนี้ เพื่อให้ลักษณะการทำงานเหมือนกับโหนดอื่นๆ เราได้สร้างคลาส TopLayerContainer ใหม่ที่ขยายคลาส UI.TreeOutline.TreeElement ซึ่งรับผิดชอบลักษณะการทำงานของโหนดฟรอนท์เอนด์

เพื่อให้ได้ตำแหน่งที่ต้องการ คลาสที่แสดงผลองค์ประกอบจะแนบ TopLayerContainer เป็นระดับข้างเคียงถัดไปของแท็ก <html>

ป้ายเลเยอร์บนสุดใหม่บ่งบอกว่าองค์ประกอบอยู่ในเลเยอร์บนสุดและทำหน้าที่เป็นลิงก์ไปยังทางลัดขององค์ประกอบนี้ในองค์ประกอบ TopLayerContainer

การออกแบบเบื้องต้น

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

การบุกรุกที่เราพบคือการสร้างลิงก์ไปยังโหนด DOM ของฟรอนท์เอนด์แทนการทำซ้ำโหนดเหล่านั้น คลาสที่มีหน้าที่สร้างลิงก์ไปยังองค์ประกอบในเครื่องมือสำหรับนักพัฒนาเว็บคือ ShortcutTreeElement ซึ่งขยาย UI.TreeOutline.TreeElement ShortcutTreeElement มีลักษณะการทำงานเหมือนกับองค์ประกอบแผนผัง DOM สำหรับเครื่องมือสำหรับนักพัฒนาเว็บอื่นๆ แต่ไม่มีโหนดที่เกี่ยวข้องในแบ็กเอนด์และมีปุ่มที่ลิงก์ไปยัง ElementsTreeElement ShortcutTreeElement แต่ละรายการไปยังโหนดเลเยอร์บนสุดมี ShortcutTreeElement ย่อยที่ลิงก์ไปยังการแสดงองค์ประกอบจำลอง ::backdrop ในแผนผัง DOM สำหรับ DevTools

การออกแบบเบื้องต้น

การออกแบบเริ่มต้น

การเปลี่ยนแปลงโปรโตคอลสำหรับนักพัฒนาเว็บใน Chrome (CDP)

คุณต้องเปลี่ยนแปลง Chrome DevTools Protocol (CDP) จึงจะใช้การรองรับเลเยอร์บนสุดได้ CDP ทำหน้าที่เป็นโปรโตคอลการสื่อสารระหว่างเครื่องมือสำหรับนักพัฒนาเว็บกับ Chromium

เราต้องเพิ่มสิ่งต่อไปนี้

  • คำสั่งสำหรับเรียกใช้จากฟรอนท์เอนด์ได้ตลอดเวลา
  • เหตุการณ์ที่ทริกเกอร์บนฟรอนท์เอนด์จากฝั่งแบ็กเอนด์

CDP: คำสั่ง DOM.getTopLayerElements

ในการแสดงองค์ประกอบเลเยอร์บนสุดในปัจจุบัน เราต้องใช้คำสั่ง CDP ทดลองใหม่ซึ่งแสดงรายการรหัสโหนดขององค์ประกอบที่อยู่ในเลเยอร์บนสุด เครื่องมือสำหรับนักพัฒนาเว็บจะเรียกใช้คำสั่งนี้เมื่อมีการเปิดเครื่องมือสำหรับนักพัฒนาเว็บหรือเมื่อองค์ประกอบของเลเยอร์ด้านบนเปลี่ยนแปลง คำสั่งจะมีลักษณะดังนี้

  # Returns NodeIds of the current top layer elements.
  # Top layer renders closest to the user within a viewport, therefore, its elements always
  # appear on top of all other content.
  experimental command getTopLayerElements
    returns
      # NodeIds of the top layer elements.
      array of NodeId nodeIds

CDP: เหตุการณ์ DOM.topLayerElementsUpdated รายการ

ในการได้รายการข้อมูลล่าสุดขององค์ประกอบเลเยอร์บนสุด เราจําเป็นต้องทำการเปลี่ยนแปลงทุกอย่างขององค์ประกอบเลเยอร์บนสุดเพื่อเรียกเหตุการณ์ CDP เวอร์ชันทดลอง เหตุการณ์นี้จะแจ้งการเปลี่ยนแปลงฟรอนท์เอนด์ซึ่งจะเรียกใช้คำสั่ง DOM.getTopLayerElements และรับรายการองค์ประกอบใหม่

กิจกรรมจะมีลักษณะดังนี้

  # Called by the change of the top layer elements.
  experimental event topLayerElementsUpdated

ข้อควรพิจารณาเกี่ยวกับ CDP

วิธีนำการรองรับ CDP ของชั้นบนสุดไปใช้นั้นมีหลายตัวเลือก อีกทางเลือกหนึ่งที่เราพิจารณาคือการสร้างเหตุการณ์ที่จะส่งคืนรายการองค์ประกอบเลเยอร์บนสุด แทนที่จะแจ้งแค่ส่วนหน้าเกี่ยวกับการเพิ่มหรือนำองค์ประกอบเลเยอร์บนสุดออก

หรืออาจสร้าง 2 เหตุการณ์แทนคำสั่ง: topLayerElementAdded และ topLayerElementRemoved ในกรณีนี้ เราจะได้รับองค์ประกอบและจำเป็นต้องจัดการอาร์เรย์ขององค์ประกอบเลเยอร์บนสุดในส่วนหน้า

ปัจจุบันเหตุการณ์ฟรอนท์เอนด์จะเรียกใช้คำสั่ง getTopLayerElements เพื่อรับรายการองค์ประกอบที่อัปเดต หากเราส่งรายการองค์ประกอบ หรือองค์ประกอบเฉพาะที่ทำให้เกิดการเปลี่ยนแปลงทุกครั้งที่ทริกเกอร์เหตุการณ์ เราอาจหลีกเลี่ยงการเรียกใช้คำสั่งเพียงขั้นตอนเดียวได้ แต่ในกรณีนี้ ฟรอนท์เอนด์จะเสียสิทธิ์ในการควบคุมว่าจะพุชองค์ประกอบใดบ้าง

เรานำมาใช้ในลักษณะนี้เพราะในความคิดของเราแล้ว จะดีกว่าหากฟรอนท์เอนด์ตัดสินใจว่าเมื่อใดที่จะขอโหนดของเลเยอร์บนสุด ตัวอย่างเช่น ถ้าเลเยอร์บนสุดถูกยุบใน UI หรือผู้ใช้ใช้แผงเครื่องมือสำหรับนักพัฒนาเว็บที่ไม่มีแผนผังองค์ประกอบ ก็ไม่จำเป็นต้องได้รับโหนดเพิ่มเติมที่อาจลึกลงไปในแผนผังได้