มุมมองที่กำหนดเองซึ่งออกแบบมาอย่างดีก็เหมือนกับชั้นเรียนอื่นๆ ที่ออกแบบมาอย่างดี โดยจะห่อหุ้มชุดฟังก์ชันการทำงานที่เฉพาะเจาะจงด้วยอินเทอร์เฟซที่เรียบง่าย ใช้ CPU และหน่วยความจำอย่างมีประสิทธิภาพ และอื่นๆ นอกเหนือจากการเป็นคลาสที่ออกแบบมาอย่างดีแล้ว มุมมองที่กำหนดเองต้องมีคุณสมบัติดังนี้
- เป็นไปตามมาตรฐาน Android
- ระบุแอตทริบิวต์ที่กำหนดเองซึ่งจัดรูปแบบได้ซึ่งทำงานร่วมกับเลย์เอาต์ XML ของ Android
- ส่งเหตุการณ์การช่วยเหลือพิเศษ
- เข้ากันได้กับแพลตฟอร์ม Android หลายแพลตฟอร์ม
เฟรมเวิร์ก Android มีชุดคลาสพื้นฐานและแท็ก XML ที่จะช่วยให้คุณสร้างมุมมองที่ เป็นไปตามข้อกำหนดทั้งหมด เหล่านี้ได้ บทเรียนนี้จะอธิบายวิธีใช้เฟรมเวิร์ก Android เพื่อสร้างฟังก์ชันหลักของคลาส View
ดูข้อมูลเพิ่มเติมได้ในคอมโพเนนต์มุมมองที่กำหนดเอง
สร้างคลาสย่อยของมุมมอง
คลาส View ทั้งหมดที่กำหนดไว้ในเฟรมเวิร์ก Android จะขยาย
View นอกจากนี้ คุณยังViewขยายมุมมองที่กำหนดเองได้โดยตรง หรือจะประหยัดเวลาด้วยการขยายคลาสย่อยของมุมมองที่มีอยู่ เช่น Button ก็ได้
หากต้องการอนุญาตให้ Android Studio โต้ตอบกับมุมมอง คุณต้องระบุตัวสร้างที่รับออบเจ็กต์ Context และ AttributeSet เป็นพารามิเตอร์อย่างน้อย
ตัวสร้างนี้ช่วยให้เครื่องมือสร้างเลย์เอาต์สร้างและแก้ไขอินสแตนซ์ของมุมมองได้
Kotlin
class PieChart(context: Context, attrs: AttributeSet) : View(context, attrs)
Java
class PieChart extends View { public PieChart(Context context, AttributeSet attrs) { super(context, attrs); } }
กำหนดแอตทริบิวต์ที่กำหนดเอง
หากต้องการเพิ่ม View ในตัวลงในอินเทอร์เฟซผู้ใช้ ให้ระบุในองค์ประกอบ XML และควบคุมลักษณะที่ปรากฏและลักษณะการทำงานด้วยแอตทริบิวต์ขององค์ประกอบ นอกจากนี้ คุณยังเพิ่มและจัดรูปแบบมุมมองที่กำหนดเองได้โดยใช้ XML หากต้องการ
เปิดใช้ลักษณะการทำงานนี้ในมุมมองที่กำหนดเอง ให้ทำดังนี้
- กำหนดแอตทริบิวต์ที่กำหนดเองสำหรับมุมมองในองค์ประกอบทรัพยากร
<declare-styleable> - ระบุค่าสำหรับแอตทริบิวต์ในการออกแบบ XML
- ดึงค่าแอตทริบิวต์ที่รันไทม์
- ใช้ค่าแอตทริบิวต์ที่ดึงมากับมุมมอง
ส่วนนี้จะอธิบายวิธีกำหนดแอตทริบิวต์ที่กำหนดเองและระบุค่าของแอตทริบิวต์ ส่วนถัดไปจะครอบคลุม การเรียกข้อมูลและการใช้ค่าที่รันไทม์
หากต้องการกำหนดแอตทริบิวต์ที่กำหนดเอง ให้เพิ่ม<declare-styleable>
ลงในโปรเจ็กต์ โดยปกติแล้วจะใส่ทรัพยากรเหล่านี้ไว้ในไฟล์
res/values/attrs.xml ตัวอย่างไฟล์ attrs.xml มีดังนี้
<resources> <declare-styleable name="PieChart"> <attr name="showText" format="boolean" /> <attr name="labelPosition" format="enum"> <enum name="left" value="0"/> <enum name="right" value="1"/> </attr> </declare-styleable> </resources>
โค้ดนี้ประกาศแอตทริบิวต์ที่กำหนดเอง 2 รายการ ได้แก่ showText และ labelPosition
ซึ่งเป็นของเอนทิตีที่จัดรูปแบบได้ชื่อ PieChart ตามธรรมเนียมแล้ว ชื่อของเอนทิตีที่จัดรูปแบบได้จะเหมือนกับชื่อของคลาสที่กำหนดมุมมองที่กำหนดเอง แม้ว่าคุณไม่จำเป็นต้องทำตามรูปแบบนี้
แต่โปรแกรมแก้ไขโค้ดยอดนิยมหลายโปรแกรม
ก็อาศัยรูปแบบการตั้งชื่อนี้เพื่อช่วยเติมคำสั่งให้สมบูรณ์
เมื่อกำหนดแอตทริบิวต์ที่กำหนดเองแล้ว คุณจะใช้แอตทริบิวต์เหล่านั้นในไฟล์ XML ของเลย์เอาต์ได้เช่นเดียวกับแอตทริบิวต์ในตัว
ความแตกต่างเพียงอย่างเดียวคือแอตทริบิวต์ที่กำหนดเองของคุณอยู่ในเนมสเปซอื่น แต่จะอยู่ใน http://schemas.android.com/apk/res/[your package name] แทนที่จะอยู่ในเนมสเปซ http://schemas.android.com/apk/res/android ตัวอย่างเช่น วิธีใช้แอตทริบิวต์
ที่กำหนดสำหรับ
PieChart มีดังนี้
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:custom="http://schemas.android.com/apk/res-auto"> <com.example.customviews.charting.PieChart custom:showText="true" custom:labelPosition="left" /> </LinearLayout>
ตัวอย่างใช้xmlnsคำสั่ง
เพื่อหลีกเลี่ยงการทำซ้ำ URI เนมสเปซที่ยาว คำสั่งนี้กำหนดชื่อแทน custom ให้กับ
เนมสเปซ http://schemas.android.com/apk/res/com.example.customviews
คุณเลือกชื่อแทนที่ต้องการสำหรับเนมสเปซได้
สังเกตชื่อแท็ก XML ที่เพิ่มมุมมองที่กำหนดเองลงในเลย์เอาต์ ซึ่งเป็นชื่อที่มีคุณสมบัติครบถ้วนของคลาสมุมมองที่กําหนดเอง หากคลาสของมุมมองเป็นคลาสภายใน ให้ระบุคลาสเพิ่มเติม
ด้วยชื่อของคลาสภายนอกของมุมมอง
เช่น คลาส
PieChart มีคลาสภายในชื่อ PieView หากต้องการใช้
แอตทริบิวต์ที่กำหนดเองจากคลาสนี้ ให้
ใช้แท็ก com.example.customviews.charting.PieChart$PieView
ใช้แอตทริบิวต์ที่กำหนดเอง
เมื่อสร้าง View จากเลย์เอาต์ XML ระบบจะอ่านแอตทริบิวต์ทั้งหมดในแท็ก XML
จากชุดทรัพยากร
และส่งไปยังตัวสร้างของ View เป็น
AttributeSet
แม้ว่าคุณจะอ่านค่าจาก AttributeSet ได้โดยตรง แต่การทำเช่นนั้นก็มีข้อเสียบางประการ ดังนี้
- ระบบจะไม่แปลงการอ้างอิงทรัพยากรภายในค่าแอตทริบิวต์
- ไม่ได้ใช้รูปแบบ
แต่ให้ส่ง AttributeSet ไปยัง
obtainStyledAttributes() แทน
เมธอดนี้จะส่งคืน
TypedArray
อาร์เรย์ของ
ค่าที่
เลิกอ้างอิงและจัดรูปแบบแล้ว
คอมไพเลอร์ทรัพยากรของ Android จะทำงานหลายอย่างให้คุณเพื่อให้การเรียกใช้
obtainStyledAttributes()
ง่ายขึ้น สำหรับทรัพยากร <declare-styleable>
แต่ละรายการในไดเรกทอรี res/ R.java ที่สร้างขึ้นจะกำหนดทั้งอาร์เรย์ของรหัสแอตทริบิวต์
และชุดค่าคงที่
ที่กำหนดดัชนีสำหรับแต่ละแอตทริบิวต์ในอาร์เรย์ คุณใช้ค่าคงที่ที่กำหนดไว้ล่วงหน้าเพื่ออ่านแอตทริบิวต์จาก TypedArray วิธีการมีดังนี้
คลาส PieChart
อ่านแอตทริบิวต์
Kotlin
init { context.theme.obtainStyledAttributes( attrs, R.styleable.PieChart, 0, 0).apply { try { mShowText = getBoolean(R.styleable.PieChart_showText, false) textPos = getInteger(R.styleable.PieChart_labelPosition, 0) } finally { recycle() } } }
Java
public PieChart(Context context, AttributeSet attrs) { super(context, attrs); TypedArray a = context.getTheme().obtainStyledAttributes( attrs, R.styleable.PieChart, 0, 0); try { mShowText = a.getBoolean(R.styleable.PieChart_showText, false); textPos = a.getInteger(R.styleable.PieChart_labelPosition, 0); } finally { a.recycle(); } }
โปรดทราบว่าออบเจ็กต์ TypedArray
เป็นทรัพยากรที่ใช้ร่วมกัน
และต้องรีไซเคิลหลังจากใช้งาน
เพิ่มพร็อพเพอร์ตี้และเหตุการณ์
แอตทริบิวต์เป็นวิธีที่มีประสิทธิภาพในการควบคุมลักษณะการทำงานและลักษณะที่ปรากฏของมุมมอง แต่จะอ่านได้ก็ต่อเมื่อมีการเริ่มต้นมุมมองเท่านั้น หากต้องการให้มีลักษณะการทำงานแบบไดนามิก ให้แสดงเครื่องมือรับและตั้งค่าพร็อพเพอร์ตี้สำหรับแอตทริบิวต์ที่กำหนดเองแต่ละรายการ ข้อมูลโค้ดต่อไปนี้แสดงวิธีที่ PieChart แสดงพร็อพเพอร์ตี้
ที่ชื่อ showText
Kotlin
fun isShowText(): Boolean { return mShowText } fun setShowText(showText: Boolean) { mShowText = showText invalidate() requestLayout() }
Java
public boolean isShowText() { return mShowText; } public void setShowText(boolean showText) { mShowText = showText; invalidate(); requestLayout(); }
โปรดทราบว่า setShowText เรียกใช้ invalidate()
และ requestLayout() การเรียกเหล่านี้มีความสําคัญ
เพื่อให้มั่นใจว่ามุมมองทํางานได้อย่างน่าเชื่อถือ คุณต้อง
ทำให้มุมมองไม่ถูกต้องหลังจากมีการเปลี่ยนแปลงคุณสมบัติที่อาจเปลี่ยนลักษณะ
ของมุมมอง เพื่อให้
ระบบทราบว่าต้องวาดใหม่ ในทำนองเดียวกัน คุณต้องขอเลย์เอาต์ใหม่ในกรณีต่อไปนี้
หากมีการเปลี่ยนแปลงพร็อพเพอร์ตี้ในลักษณะ
ที่อาจส่งผลต่อขนาดหรือรูปร่างของมุมมอง การลืมเรียกใช้เมธอดเหล่านี้อาจทำให้เกิดข้อบกพร่องที่
ค้นหายาก
นอกจากนี้ มุมมองที่กำหนดเองต้องรองรับเครื่องมือฟังเหตุการณ์เพื่อสื่อสารเหตุการณ์สำคัญด้วย เช่น PieChart
จะแสดงเหตุการณ์ที่กำหนดเองชื่อ OnCurrentItemChanged เพื่อแจ้งให้ผู้ฟังทราบว่า
ผู้ใช้หมุน
แผนภูมิวงกลมเพื่อโฟกัสที่ชิ้นใหม่
คุณอาจลืมแสดงพร็อพเพอร์ตี้และเหตุการณ์ได้ง่าย โดยเฉพาะเมื่อคุณเป็นผู้ใช้เพียงคนเดียว ของมุมมองที่กําหนดเอง การใช้เวลาในการกำหนดอินเทอร์เฟซของมุมมองอย่างรอบคอบจะช่วยลดต้นทุนการบำรุงรักษาในอนาคต กฎที่ดีที่ควรปฏิบัติตามคือการเปิดเผยพร็อพเพอร์ตี้ใดๆ ที่ส่งผลต่อลักษณะหรือลักษณะการทำงานที่มองเห็นได้ของมุมมองที่กำหนดเองเสมอ
ออกแบบเพื่อการช่วยเหลือพิเศษ
มุมมองที่กำหนดเองต้องรองรับผู้ใช้ในวงกว้าง ซึ่งรวมถึงผู้ใช้ที่มี ความพิการที่ ทำให้มองไม่เห็นหรือใช้หน้าจอสัมผัสไม่ได้ หากต้องการสนับสนุนผู้ใช้ที่เป็นคนพิการ ให้ทำดังนี้
- ติดป้ายกำกับช่องป้อนข้อมูลโดยใช้แอตทริบิวต์
android:contentDescription - ส่งเหตุการณ์การช่วยเหลือพิเศษโดยการเรียกใช้
sendAccessibilityEvent()เมื่อเหมาะสม - รองรับตัวควบคุมทางเลือก เช่น D-pad หรือแทร็กบอล
ดูข้อมูลเพิ่มเติมเกี่ยวกับการสร้างมุมมองที่เข้าถึงได้ที่ ทำให้แอปเข้าถึงได้ง่ายขึ้น