การจัดการปลั๊กไฟ

ความสามารถในการแสดงผล (เช่น โหมดการแสดงผลและประเภท HDR ที่รองรับ) สามารถเปลี่ยนแบบไดนามิกบนอุปกรณ์ที่มีจอแสดงผลเชื่อมต่อภายนอก (ที่มี HDMI หรือ DisplayPort) เช่น อุปกรณ์รับสัญญาณ (STB) ของ Android TV และอุปกรณ์การแพร่ภาพและเสียงผ่านโครงข่ายอินเทอร์เน็ต (Over The Top หรือ OTT) การเปลี่ยนแปลงนี้อาจเกิดขึ้นจากสัญญาณปลั๊กฮอต HDMI เช่น เมื่อผู้ใช้เปลี่ยนจากจอแสดงผลหนึ่งไปยังอีกจอแสดงผลหนึ่ง หรือเปิดเครื่องอุปกรณ์โดยไม่ได้เชื่อมต่อจอแสดงผล Android 12 ขึ้นไปมีการเปลี่ยนแปลงด้านเฟรมเวิร์กในการจัดการกับเทคโนโลยีปลั๊กอินร้อนและความสามารถในการแสดงผลแบบไดนามิก

หน้านี้อธิบายการจัดการ HotPlug ของ Display และการเปลี่ยนแปลงความสามารถในการแสดงผลในการใช้งาน Composer HAL นอกจากนี้ยังมีการกล่าวถึงวิธีจัดการเฟรมบัฟเฟอร์ที่เกี่ยวข้องและป้องกันสภาวะการแข่งขันในสถานการณ์เหล่านี้

อัปเดตความสามารถในการแสดงผล

ส่วนนี้อธิบายวิธีที่เฟรมเวิร์ก Android จัดการกับการเปลี่ยนแปลงความสามารถในการแสดงผลที่เริ่มต้นโดย Composer HAL

ก่อนที่ Android จะจัดการการเปลี่ยนแปลงความสามารถในการแสดงผลได้อย่างถูกต้อง OEM ต้องใช้ HAL ของ Composer เพื่อใช้ onHotplug(display, connection=CONNECTED) เพื่อแจ้งเฟรมเวิร์กเกี่ยวกับการเปลี่ยนแปลงความสามารถในการแสดงผล หลังจากที่ได้ใช้งาน Android จะจัดการกับการเปลี่ยนแปลงด้านความสามารถในการแสดงผล ดังนี้

  1. เมื่อตรวจหาการเปลี่ยนแปลงของความสามารถในการแสดงผล เฟรมเวิร์กจะได้รับการแจ้งเตือน onHotplug(display, connection=CONNECTED)
  2. เมื่อได้รับการแจ้งเตือน เฟรมเวิร์กจะยกเลิกสถานะการแสดงผลและสร้างขึ้นใหม่ด้วยความสามารถใหม่จาก HAL โดยใช้เมธอด getActiveConfig, getDisplayConfigs, getDisplayAttribute, getColorModes, getHdrCapabilities และ getDisplayCapabilities
  3. หลังจากที่เฟรมเวิร์กสร้างสถานะการแสดงผลใหม่ขึ้นแล้ว ระบบจะส่งการเรียกกลับ onDisplayChanged ไปยังแอปที่กําลังรอฟังเหตุการณ์ดังกล่าวอยู่

เฟรมเวิร์กนี้จะจัดสรร Framebuffer อีกครั้งในเหตุการณ์ onHotplug(display, connection=CONNECTED) ที่ตามมา ดูการจัดการเฟรมบัฟเฟอร์ของไคลเอ็นต์ เพื่อดูข้อมูลเพิ่มเติมเกี่ยวกับวิธีจัดการหน่วยความจำของเฟรมบัฟเฟอร์อย่างเหมาะสมเพื่อหลีกเลี่ยงการทำงานล้มเหลวระหว่างการจัดสรรเฟรมบัฟเฟอร์ใหม่

จัดการกับสถานการณ์การเชื่อมต่อทั่วไป

ส่วนนี้จะพูดถึงวิธีจัดการสถานการณ์การเชื่อมต่อต่างๆ อย่างเหมาะสมในขั้นตอนการติดตั้งใช้งาน เมื่อจอแสดงผลหลักเชื่อมต่อและไม่ได้เชื่อมต่อ

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

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

สถานการณ์ การใช้งาน
ไม่มีจอแสดงผลที่เชื่อมต่อเมื่อเปิดเครื่อง
  • ส่งสัญญาณ onHotplug(display, connection=CONNECTED) จาก HAL ของ Composer ไปยังเฟรมเวิร์ก
  • แทนที่สถานะการแสดงผลจริงภายใน HAL ของ Composer ด้วยสถานะการแสดงผลตัวยึดตำแหน่ง
จอแสดงผลหลักเชื่อมต่อกัน
  • ส่งเหตุการณ์ onHotplug(display, connection=CONNECTED) อื่นจาก HAL ของ Composer ไปยังเฟรมเวิร์ก

    ซึ่งจะทําให้เฟรมเวิร์กโหลดความสามารถในการแสดงผลทั้งหมดซ้ำ

จอแสดงผลหลักถูกตัดการเชื่อมต่อ
  • ส่งเหตุการณ์ onHotplug(display, connection=CONNECTED) อื่นจาก HAL ของ Composer ไปยังเฟรมเวิร์ก
  • แทนที่สถานะการแสดงผลจริงภายใน HAL ของ Composer ด้วยสถานะการแสดงผลตัวยึดตำแหน่ง การแสดงตัวยึดตําแหน่งต้องมีโหมดการแสดงผลเดียวเพื่อให้เฟรมเวิร์กส่ง Callback onDisplayChanged ไปยังแอป (เนื่องจากชุดโหมดที่รองรับมีการเปลี่ยนแปลง) โหมดการแสดงผลเดียวนี้ต้องตรงกับโหมดที่ใช้งานล่าสุดของจอแสดงผลจริงก่อนยกเลิกการเชื่อมต่อ เพื่อให้แอปไม่ได้รับเหตุการณ์การเปลี่ยนแปลงการกำหนดค่า

ข้อควรพิจารณาเกี่ยวกับการเชื่อมต่อที่ไม่ใช่ HDMI

Android TV รองรับความละเอียดต่อไปนี้เท่านั้น

  • 720x1280
  • 1080x1920
  • 2160x3840
  • 4320x7680

เมื่อ STB หรือดองเกิลทีวีพยายามแสดงความละเอียดที่ไม่รองรับ เช่น 480i ผ่านการเชื่อมต่อ CVBS ระบบจะแสดงข้อความแสดงข้อผิดพลาดให้แก่ผู้ใช้

หาก STB หรือดองเกิลทีวีมีทั้งการเชื่อมต่อ HDMI และไม่ใช่ HDMI การเชื่อมต่อ HDMI จะเป็นจอหลักและการเชื่อมต่อที่ไม่ใช่ HDMI จะไม่มีการใช้งาน ดังนั้น หากไม่ได้เชื่อมต่อ HDMI ในขณะที่ยังเชื่อมต่อที่ไม่ใช่ HDMI ระบบจะส่งเหตุการณ์ไปยัง SurfaceFlinger และความสามารถของจอแสดงผลที่ไม่ใช่ HDMI จะต้องแสดงผ่าน getDisplayAttribute และ API iComposerClient อื่นๆ (เช่น getHdrCapabilities)

ใช้รหัสการกำหนดค่าตามลำดับเพื่อป้องกันเงื่อนไขการแข่งขัน

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

ส่วนนี้อธิบายวิธีการของเงื่อนไขการแข่งขัน ตามด้วยรายละเอียดเกี่ยวกับวิธีติดตั้งใช้งาน HAL ของคอมโพสเซอร์ เพื่อให้ใช้รหัสตามลำดับเพื่อป้องกันเงื่อนไขดังกล่าว

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

  1. รหัสการกำหนดค่าการแสดงผลที่รองรับมีดังนี้

    • id=1, 1080x1920 60 Hz
    • id=2, 1080x1920 50 Hz
  2. เฟรมเวิร์กนี้เรียกใช้ setActiveConfig(display, config=1)

  3. ในขณะเดียวกัน HAL ของ Composer จะประมวลผลการเปลี่ยนแปลงการกำหนดค่าการแสดงผลและอัปเดตสถานะภายในเป็นการกำหนดค่าการแสดงผลชุดใหม่ดังต่อไปนี้

    • id=1, 2160x3840 60 Hz
    • id=2, 2160x3840 50 Hz
    • id=3, 1080x1920 60 Hz
    • id=4, 1080x1920 50 Hz
  4. HAL ของคอมโพสเซอร์จะส่งเหตุการณ์ onHotplug ไปยังเฟรมเวิร์กเพื่อแจ้งให้ทราบว่าชุดโหมดที่รองรับมีการเปลี่ยนแปลง

  5. HAL ของคอมโพสเซอร์จะได้รับ setActiveConfig(display, config=1) (จากขั้นตอนที่ 2)

  6. HAL จะตีความว่าเฟรมเวิร์กได้ขอให้เปลี่ยนการกำหนดค่าเป็น 2160x3840 60 Hz แม้ว่าในความเป็นจริงแล้วจะต้องการให้เป็น 1080x1920 60 Hzก็ตาม

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

กำหนดค่า HAL ของคอมโพสเซอร์เพื่อใช้รหัสตามลำดับ

โดย OEM จะต้องใช้ HAL ของคอมโพสเซอร์ดังนี้เพื่อหลีกเลี่ยงเงื่อนไขการแข่งขันนี้

  • เมื่อ HAL ของคอมโพสเซอร์อัปเดตการกำหนดค่าการแสดงผลที่รองรับ จะมีการกำหนดรหัสตามลำดับใหม่ให้กับการกำหนดค่าการแสดงผลใหม่
  • เมื่อเฟรมเวิร์กเรียกใช้ setActiveConfig หรือ setActiveConfigWithConstraints ที่มีรหัสการกำหนดค่าไม่ถูกต้อง Composer HAL จะไม่สนใจการเรียกใช้

ขั้นตอนเหล่านี้มีไว้เพื่อป้องกันสภาวะการแข่งขันดังที่แสดงในการอภิปรายต่อไปนี้

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

  1. รหัสการกำหนดค่าการแสดงผลที่รองรับมีดังนี้

    • id=1, 1080x1920 60 Hz
    • id=2, 1080x1920 50 Hz
  2. เฟรมเวิร์กนี้เรียกใช้ setActiveConfig(display, config=1)

  3. เมื่อประมวลผลการเปลี่ยนแปลงการกำหนดค่าการแสดงผลแล้ว ระบบจะกำหนดรหัสการกำหนดค่าชุดถัดไปโดยเริ่มจากจำนวนเต็มถัดไปที่ไม่มีการใช้งาน ดังต่อไปนี้

    • id=3, 2160x3840 60 Hz

    • id=4, 2160x3840 50 Hz

    • id=5, 1080x1920 60 Hz

    • id=6, 1080x1920 50 Hz

  4. HAL ของคอมโพสเซอร์จะส่งเหตุการณ์ onHotplug ไปยังเฟรมเวิร์กเพื่อแจ้งให้ทราบว่าชุดโหมดที่รองรับมีการเปลี่ยนแปลง

  5. HAL ของคอมโพสเซอร์จะได้รับ setActiveConfig(display, config=1) (จากขั้นตอนที่ 2)

  6. HAL ของ Composer จะไม่สนใจการเรียกใช้เนื่องจากรหัสดังกล่าวใช้ไม่ได้อีกต่อไป

  7. เฟรมเวิร์กจะได้รับและประมวลผลเหตุการณ์ onHotplug จากขั้นตอนที่ 4 โดยจะเรียกใช้ HAL ของคอมโพสเซอร์โดยใช้ฟังก์ชัน getDisplayConfigs และ getDisplayAttribute เมื่อใช้ฟังก์ชันเหล่านี้ เฟรมเวิร์กจะระบุรหัสใหม่ (5) สำหรับความละเอียดและอัตราการรีเฟรชที่ต้องการที่ 1080x1920 และ 60 Hz

  8. เฟรมเวิร์กจะส่งเหตุการณ์ setActiveConfig อีกครั้งที่มีรหัสที่อัปเดตแล้วเป็น 5

  9. HAL ของคอมโพสเซอร์จะได้รับ setActiveConfig(display, config=5) จากขั้นตอนที่ 5

  10. HAL ตีความอย่างถูกต้องว่าเฟรมเวิร์กได้ขอเปลี่ยนการกำหนดค่าเป็น 1080x1920 60 Hz

ดังที่แสดงในตัวอย่างด้านบน กระบวนการที่ใช้การกำหนดรหัสตามลำดับจะช่วยยืนยันว่าจะป้องกันเงื่อนไขการแข่งขัน และมีการอัปเดตการเปลี่ยนแปลงการกำหนดค่าการแสดงผลที่ถูกต้อง