วันจันทร์ที่ 14 ธันวาคม พ.ศ. 2558

onSaveInstanceState()

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

ยกตัวอย่างเช่น ผู้ใช้กำลังทำข้อสอบถึงข้อที่ 5 บังเอิญว่า อยากจะอ่านข้อความตามแนวนอน จึงหมุนหน้าจอ จากแนวตั้งมาดูตามแนวนอน แต่ผลปรากฏว่า ข้อสอบจากข้อที่ 5 กลับมาเป็นข้อ 1
ที่เป็นเช่นนี้เพราะ เมื่อมีการเปลี่ยนแนว หรือ Orientation ของมือถือ วงจรชีวิตของหน้าจอนั้น ๆ จะยุติลง และเริ่มต้นใหม่ โดยใช้ค่าเริ่มต้นที่มีอยู่ ดังนั้นจึงกลับไปสู่สภาพเดิม

การจัดเก็บสภาพของหน้าจอ ด้วย onSaveInstanceState()

ในกรณีตัวอย่างข้อสอบข้างต้น มีการกำหนดตัวแปรคือ thisQuestionNum เพื่อเก็บหมายเลขข้อของข้อสอบ เพื่อนำข้อสอบมาแสดงตามหมายเลขนั้น ๆ โดยเริ่มต้นจากข้อ 1 และ ผู้ใช้สามารถคลิกเพิ่มไปดู ข้อ 2,3,4  ... ได้ตามลำดับ ซึ่งจะทำให้ค่าของตัวแปร thisQuestionNum เปลี่ยนไป ตามที่ผู้ใช้คลิก

ดังนั้น การจัดเก็บสภาพจึงต้องจัดเก็บค่าของตัวแปร thisQuestionNum  และนำไปใช้ เมื่อมีการ Create หน้าจอนี้

การจัดเก็บสภาพ ให้กำหนดเป็น Method ใหม่ อยู่นอก onCreate() method ดังนี้

@Overrideprotected void onSaveInstanceState(Bundle outState) {
    outState.putInt("thisQuestionNum", thisQuestionNum);
    super.onSaveInstanceState(outState);
}

การจัดเก็บข้อมูล จะเก็บไว้ใน Bundle Object และเนื่องจาก thisQuestionNum เป็นตัวเลข จึงต้องใช้ .putInt เพื่อเก็บข้อมูล การจัดเก็บจะเก็บในลักษณะ Name:Value pair โดยที่เมื่อจะเรียกใช้ จะเรียกชื่อที่อยู่ในเครื่องหมายคำพูด

Android จะเรียกใช้ Method นี้ ก่อนที่หน้าจอจะหมดสภาพ หรือ ถูก destroy และเมื่อเริ่มต้นใหม่ โดยปกติ Android จะมีการตรวจสอบอยู่แล้วใน onCreate() method 

@Overrideprotected void onCreate(Bundle savedInstanceState) {

.....
}

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

@Overrideprotected void onCreate(Bundle savedInstanceState) {

    if (savedInstanceState != null) {
        // ใช้ค่าที่เก็บไว้        thisQuestionNum = savedInstanceState.getInt("thisQuestionNum");
    } else {
        // กำหนดเป็นค่าเริ่มต้น        thisQuestionNum = 0;
    }

    super.onCreate(savedInstanceState);

......

}

เมื่อมีการเปลี่ยนแนวหน้าจอ ข้อมูลจะไม่เปลี่ยนไป ข้อมูลจะเหมือนเดิม ไม่ว่าจะเป็นแนวตั้ง หรือแนวนอน ก็ตาม




ไม่มีความคิดเห็น:

แสดงความคิดเห็น