Cutouts ใน Compose

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

ตัวอย่างการตัดภาพในโหมดภาพบุคคล
รูปที่ 1 ตัวอย่างคัตเอาต์ในโหมดแนวตั้ง
ตัวอย่างการตัดออกในโหมดแนวนอน
ภาพที่ 2 ตัวอย่างคัตเอาต์ในโหมดแนวนอน

Android รองรับหน้าจอรอยบากในอุปกรณ์ที่ใช้ Android 9 (API ระดับ 28) ขึ้นไป อย่างไรก็ตาม ผู้ผลิตอุปกรณ์ยังรองรับส่วนตัดบนจอแสดงผลในอุปกรณ์ที่ใช้ Android 8.1 หรือต่ำกว่าได้ด้วย

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

เคสเริ่มต้น

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

ตัวอย่างเช่น เมื่อคุณใช้ Modifier.windowInsetsPadding(WindowInsets.safeContent) หรือ Modifier.windowInsetsPadding(WindowInsets.safeDrawing) แอปจะไม่วาดในพื้นที่ที่มีการวางรูปภาพตัดออกโดยอัตโนมัติ ทั้ง WindowInsets.safeContent และ WindowInsets.safeDrawing มีข้อมูลส่วนที่ถูกตัดออกของจอแสดงผลและจะไม่วาดภาพในส่วนที่ถูกตัดออกของอุปกรณ์

override fun onCreate(savedInstanceState: Bundle?) {
    super.onCreate(savedInstanceState)

    WindowCompat.setDecorFitsSystemWindows(window, false)

    setContent {
        Box(Modifier.windowInsetsPadding(WindowInsets.safeContent)) {
            // Any composable inside here will avoid drawing behind cutouts
        }
    }
}

หากต้องการปรับแต่งลักษณะการทำงานนี้เพิ่มเติม คุณต้องจัดการข้อมูลการตัดออกด้วยตนเอง

จัดการข้อมูลที่ถูกตัดออกด้วยตนเอง

คุณจัดการรูปภาพที่ตัดออกได้ด้วยวิธีใดก็ได้ต่อไปนี้

สําหรับคอมโพสิท เราขอแนะนําให้ตั้งค่า windowLayoutInDisplayCutoutMode เป็น default ในธีมโดยรวม จากนั้นใช้ประโยชน์จาก WindowInsets.displayCutout เพื่อจัดการส่วนแทรกในคอมโพสิท ดังนี้

Canvas(modifier = Modifier.fillMaxSize().windowInsetsPadding(WindowInsets.displayCutout)) {
    drawRect(Color.Red, style = Stroke(2.dp.toPx()))
}

วิธีนี้ช่วยให้คุณใช้ระยะห่างจากขอบของ displayCutout ได้เมื่อจำเป็น หรือละเว้นระยะห่างจากขอบดังกล่าวก็ได้หากไม่จำเป็น

หรือคุณอาจใช้การตั้งค่าเดียวกับที่เอกสารประกอบเกี่ยวกับ Views Cutout อธิบายโดยตั้งค่าธีมกิจกรรม android:windowLayoutInDisplayCutoutMode เป็นอีกตัวเลือกหนึ่ง หรือตั้งค่าแอตทริบิวต์หน้าต่างโดยใช้ window.attributes.layoutInDisplayCutoutMode = LAYOUT_IN_DISPLAY_CUTOUT_MODE_DEFAULT อย่างไรก็ตาม ระบบจะใช้โหมดการตัดออกกับกิจกรรมทั้งหมด และไม่สามารถควบคุมแยกตามองค์ประกอบแต่ละรายการได้

หากต้องการคำนึงถึงส่วนเว้าของจอแสดงผลในคอมโพสบางรายการแต่ไม่คำนึงถึงคอมโพสอื่นๆ ให้ใช้ WindowInset.displayCutout API นี้ช่วยให้คุณเข้าถึงข้อมูลการตัดออกได้เมื่อจำเป็น

แนวทางปฏิบัติแนะนำ

เมื่อทำงานกับหน้าจอรอยบาก ให้พิจารณาสิ่งต่อไปนี้

  • โปรดคำนึงถึงตําแหน่งองค์ประกอบที่สําคัญของ UI อย่าให้บริเวณที่ตัดออกบดบังข้อความ การควบคุม หรือข้อมูลสำคัญ
  • อย่าวางหรือขยายองค์ประกอบแบบอินเทอร์แอกทีฟที่ต้องใช้การจดจำการสัมผัสที่ละเอียดในพื้นที่ที่ถูกตัดออก ความไวต่อการสัมผัสอาจต่ำ ในบริเวณที่ตัดออก
  • เมื่อทำตามคำแนะนำแบบเต็มหน้าจอ ข้อมูลส่วนที่ถูกตัดออกจะรวมอยู่ในส่วนย่อย safeDrawing / safeContent
  • ใช้ Modifier.windowInsetsPadding(WindowInsets.safeDrawing) เพื่อกำหนดระยะห่างจากขอบที่เหมาะสมกับเนื้อหาของคุณ หากเป็นไปได้ หลีกเลี่ยงการฮาร์ดโค้ดความสูงของแถบสถานะ เนื่องจากอาจทำให้เนื้อหาทับซ้อนกันหรือถูกตัดออก

ทดสอบการแสดงผลเนื้อหาด้วยคัตเอาต์

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

  1. เปิดใช้ตัวเลือกสำหรับนักพัฒนาแอป
  2. ในหน้าจอตัวเลือกสำหรับนักพัฒนาซอฟต์แวร์ ให้เลื่อนลงไปที่ส่วนการวาด แล้วเลือกจำลองการแสดงผลที่มีรอยบาก
  3. เลือกประเภทรูปภาพ
    การจําลองรอยบากของจอแสดงผลในโปรแกรมจําลอง
    รูปที่ 3 ใช้ตัวเลือกสำหรับนักพัฒนาแอปเพื่อทดสอบการแสดงผลของเนื้อหา