[Dev] ห่อให้ด้วย~!! แนะนำการใช้งาน Parceler Library สำหรับ Android

มีใครเคยนำข้อมูลที่เยอะ ๆ โยนข้าม Activity บ้างไม๊ครับ รวมถึงการ Save/Restore State ด้วยนะ ถ้าเคยทำ ก็จะรู้ว่า ต้องมาเขียนคำสั่งเพื่อเก็บข้อมูลลง Bundle หรือ Intent ก่อน ด้วย Method put ทั้งหลาย ก่อนจะส่งข้อมูลไป ซึ่งจะมีชนิดตัวแปรมากมายให้เราเลือกใช้ แต่ว่ามันไม่สามารถที่จะ put Object ลงไปได้…

Android-Developer-logo_Parceler-Library

ถ้าอยากจะส่ง Object สามารถทำได้ด้วยการทำ Serialization นั่นเอง ซึ่งใน Bundle และ Intent จะสามารถ put ได้ 2 ชนิด ก็คือ Serializable และ Parcelable ซึ่งทั้งคู่ เป็น Interface นั่นหมายความว่า เราต้อง Implement Interface ไปยัง Class ก่อน ถึงจะใช้งานได้

สำหรับบน Android นั้น Parcelable เป็นวิธีที่จะทำ Serialize และ Deserialize ซึ่งทำงานได้เร็วกว่าวิธีอื่น ๆ ถึง 10 เท่า!! ถ้าอย่างงั้นแล้วจะรออะไรอีก ไป Implement Interface Parcelable กันเถอะครับ

Code ด้านล่างนี้ เป็นตัวอย่างการ Implement Interface Parcelable จาก Android Developer Reference จะเห็นว่า การใช้ Parcelable นั้น มีความยุ่งยากพอสมควร เพราะต้อง Implement Method writeToParcel(), createFromParcel() และ Inner Class CREATOR ที่ Implement Interface Parcelable.Creator<T> ด้วย ตามที่ได้ไฮไลท์ไว้ใน Code ด้านล่าง เพื่อที่จะเก็บค่าตัวแปรลงไปยัง Class Parcel

 

แต่เดี๋ยวก่อน~!! ถ้าอยากเก็บ Object ลง Parcel ตรง ๆ ก็ยังทำไม่ได้นะ ทำได้แต่ตัวแปรธรรมดา ถ้าอยากเก็บ Object ลงไป ต้อง Implement Interface IBinder ก่อน ถึงจะยัดลงไปได้

ปวดหัวกันแล้วใช่ไม๊ครับ กว่าจะยัด Object ลงไปได้ ไม่ใช่เรื่องเล่น ๆ

งั้นเอาใหม่… ถ้าเราสามารถยัด Object ลง Bundle หรือ Intent โดยสามารถเขียนคำสั่งให้จบได้ภายใน 1 บรรทัด เอาม๊า ๆ

เชิญตามมาทางนี้ครับ ผมขอแนะนำ Parceler Library ที่จะช่วยให้การสร้าง Parcelable นั้น เป็นเรื่องง่าย ๆ

 

List of contents

 

How to use Parceler

ก่อนอื่น ต้องทำการเพิ่ม Library ให้กับ Project ของเราซะก่อน สำหรับ Android Studio นั้น สามารถเพิ่ม Dependency ใน build.gradle ของ Module app เรา ดังนี้

แล้วทำการ Sync ให้เรียบร้อย เป็นอันว่า ใช้ Parceler ได้แล้ว

ตรวจสอบ Version ล่าสุดของ Parceler Library ได้ที่ http://parceler.org/

 

Annotation

สำหรับ Parceler นั้น จะให้เราระบุ Annotation @Parcel ไว้ที่ Class ที่เราจะใช้เก็บข้อมูล

Class ด้านล่างนี้ ผมออกแบบให้เก็บข้อมูล 3 ตัวด้วยกัน คือ fullname, gender และ age โดยจะใช้ Constructor ในการรับข้อมูลเข้ามา และมี Getter Method สำหรับอ่านค่าออกไป ดังนี้

ลอง Build ดู จะพบกับ Error ดังนี้

Gradle Console แสดง Error จาก Parceler Library
Gradle Console แสดง Error จาก Parceler Library

สาเหตุก็เนื่องมาจาก Parceler หา Annotation @ParcelConstructor และ Default Constructor ไม่เจอ ก็แก้ไขได้ 2 วิธี ก็คือ แปะ Annotation @ParcelConstructor ที่ Constructor ของเรา ดังนี้

หรือว่าจะสร้าง Default Constructor เปล่า ๆ ขึ้นมาก็ได้ ดังนี้

คราวนี้ลอง Build ดูใหม่ จะพบกับ Warning แทน ดังนี้

Gradle Console แสดง Warning จาก Parceler Library
Gradle Console แสดง Warning จาก Parceler Library

คราวนี้แค่เตือนเฉย ๆ สิ่งที่เตือนคือ ห้ามประกาศ Field เป็น Private เพราะฉะนั้นก็ลบทิ้งโลด

สุดท้ายก็จะได้ Class ที่แปะ Annotation @Parcel พร้อมใช้งานกับ Paceler แล้ว

 

Wrap

Wrap ก็คือการใช้ Parceler ทำการ “ห่อ” Object ไว้ ก่อนอื่นขอสร้าง Object จาก Class Person ที่สร้างไว้ก่อน

เมื่อได้ Object มาแล้ว ก็จัดการ Wrap ซะ Method wrap() ของ Class Parcels ก็จะได้ Parcelable ออกมา ด้วยคำสั่งดังนี้

ง่ายมะ ๆ

 

Unwrap

เมื่อห่อแล้ว ก็ต้องมีการ “แกะห่อ” โดยเราจะใช้ Method unwrap() ของ Class Parcels ดังนี้

ก็จะได้ Object กลับคืนมาแล้วววววววววว

ลอง get ข้อมูลออกมาจาก Object ดู ก็จะได้ข้อมูลเหมือนเดิมเป๊ะ ๆ เด๊ะ ๆ

ง่ายอีกแล้วเน๊อะ~!!

 

Add to Bundle

คราวนี้เราลองเอามาใช้กับ Bundle ดูบ้าง โดยจุดที่เราจะได้ใช้ Bundle บ่อย ๆ เลยนั่นก็คือเรื่องของการ Save/Restore State กันบ้าง…

ในการ Save State บน Method onSaveInstanceState() นั้น จะมี Parameter ชนิด Bundle ส่งมาให้เราด้วย เราสามารถใช้ Method putParcelable() ของ Bundle ในการเก็บ “ห่อ” ของ Object ได้ดังนี้

ส่วนการ Restore State บน Method onRestoreInstanceState() ก็จะมี Bundle ส่งมาให้เช่นกัน ก็ใช้ Method getParcelable() ของ Bundle ในการนำ “ห่อ” ของ Object ออกมาได้

หรือจะทำบน Method onCreate() ก็ได้เหมือนกัน

 

Add to Intent

สำหรับการใช้งานกับ Intent ซึ่งโดยส่วนใหญ่เราจะใช้ฝากข้อมูล เพื่อส่งข้าม Activity นั่นเอง

การเก็บ Parcelable ลง Intent ก็แค่เรียกใช้งาน Method putExtra() ของ Intent ก็สามารถเก็บ “ห่อ” ของ Object ลงไปได้แล้ว

ส่วนการนำ “ห่อ” ของ Object ออกมาจาก Intent ก็สามารถใช้ Method getParcelableExtra() ของ Intent ในการนำ “ห่อ” ของ Object ออกมา

เราก็สามารถใช้ Parceler ร่วมกับ Intent ได้แล้ว

 

Configuring Proguard

สำหรับการเปิดใช้งาน Proguard จะต้องกำหนดในไฟล์ Proguard เพิ่มดังนี้

 

สำหรับการใช้งาน Parceler Library แบบอื่น ๆ และการใช้งานที่ Advance กว่านี้ สามารถศึกษาต่อได้จากที่ http://parceler.org/

ส่วน Code ตัวอย่างในบทความนี้ ผมนำไปเขียนเป็น App ตัวอย่าง โดยจะมีการนำ Parceler ร่วมกับ Bundle ในการทำเรื่อง Save/Restore State และการนำ Parceler ร่วมกับ Intent ในการส่งข้อมูลข้าม Activity ทั้งไปและกลับ ลองไปดู Code กันต่อที่ Project ของผม บน GitHub นะครับ

 

บทความแนะนำ

Leave a Reply

Your email address will not be published. Required fields are marked *

 

This site uses Akismet to reduce spam. Learn how your comment data is processed.