ขออัปเดตตำแหน่ง

การใช้ข้อมูลตำแหน่งอย่างเหมาะสมอาจเป็นประโยชน์ต่อผู้ใช้แอป เช่น หากแอปช่วยให้ผู้ใช้หาเส้นทางขณะเดินหรือขับรถ หรือหากแอปติดตามตำแหน่งของเนื้อหา แอปก็จะต้องได้รับตำแหน่งของอุปกรณ์เป็นระยะๆ นอกจากสถานที่ตั้งทางภูมิศาสตร์ (ละติจูดและลองจิจูด) แล้ว คุณอาจต้องการให้ข้อมูลเพิ่มเติมแก่ผู้ใช้ เช่น ทิศทาง (ทิศทางการเคลื่อนที่ในแนวนอน) ความสูง หรือความเร็วของอุปกรณ์ ข้อมูลนี้และข้อมูลอื่นๆ มีอยู่ในออบเจ็กต์ Location ที่แอปสามารถดึงข้อมูลจากผู้ให้บริการตำแหน่งแบบรวม ด้วยเหตุนี้ API จึงอัปเดตแอปเป็นระยะๆ ด้วยตำแหน่งที่ดีที่สุดที่พร้อมใช้งาน โดยอิงตามผู้ให้บริการตำแหน่งที่พร้อมใช้งานในปัจจุบัน เช่น Wi-Fi และ GPS (ระบบกำหนดตำแหน่งทั่วโลก) ความแม่นยำของตำแหน่งจะขึ้นอยู่กับผู้ให้บริการ, สิทธิ์เข้าถึงตำแหน่งที่คุณขอ และตัวเลือกที่คุณตั้งค่าในคำขอตำแหน่ง

บทเรียนนี้จะแสดงวิธีขอการอัปเดตตำแหน่งของอุปกรณ์เป็นประจําโดยใช้เมธอด requestLocationUpdates() ในผู้ให้บริการตำแหน่งแบบรวม

รับตำแหน่งที่รู้จักล่าสุด

ตำแหน่งสุดท้ายที่ทราบของอุปกรณ์จะมีฐานที่สะดวกสำหรับการเริ่มต้น เพื่อให้แน่ใจว่าแอปมีตำแหน่งที่รู้จักก่อนเริ่มการอัปเดตตำแหน่งเป็นครั้งคราว บทเรียนเกี่ยวกับการรับตำแหน่งล่าสุดที่ทราบจะแสดงวิธีรับตำแหน่งล่าสุดที่ทราบโดยการโทรไปที่ getLastLocation() ข้อมูลโค้ดในส่วนต่อไปนี้จะถือว่าแอปของคุณได้เรียกข้อมูลตำแหน่งที่ทราบล่าสุดและจัดเก็บเป็นออบเจ็กต์ Location ในตัวแปรร่วม mCurrentLocation แล้ว

ส่งคำขอตำแหน่ง

ก่อนที่จะขอการอัปเดตตำแหน่ง แอปของคุณต้องเชื่อมต่อกับบริการตำแหน่งและส่งคำขอตำแหน่ง บทเรียนเรื่องการเปลี่ยนการตั้งค่าตำแหน่งจะแสดงวิธีการ เมื่อมีการส่งคำขอตำแหน่งแล้ว คุณจะเริ่มการอัปเดตตามปกติได้โดยโทรไปที่ requestLocationUpdates()

ผู้ให้บริการ Fused Location จะเรียกใช้เมธอด Callback LocationCallback.onLocationResult() และส่งต่อรายการออบเจ็กต์ Location หรือออก PendingIntent ที่มีตำแหน่งในข้อมูลแบบขยาย ทั้งนี้ขึ้นอยู่กับรูปแบบของคำขอ ความแม่นยำและความถี่ในการอัปเดตจะขึ้นอยู่กับสิทธิ์เข้าถึงตำแหน่งที่คุณขอและตัวเลือกที่คุณตั้งค่าไว้ในออบเจ็กต์คำขอตำแหน่ง

บทเรียนนี้แสดงวิธีรับการอัปเดตโดยใช้วิธี Callback ของ LocationCallback เรียกใช้ requestLocationUpdates() โดยส่งอินสแตนซ์ของออบเจ็กต์ LocationRequest และ LocationCallback กำหนดเมธอด startLocationUpdates() ดังที่แสดงในตัวอย่างโค้ดต่อไปนี้

Kotlin

override fun onResume() {
    super.onResume()
    if (requestingLocationUpdates) startLocationUpdates()
}

private fun startLocationUpdates() {
    fusedLocationClient.requestLocationUpdates(locationRequest,
            locationCallback,
            Looper.getMainLooper())
}

Java

@Override
protected void onResume() {
    super.onResume();
    if (requestingLocationUpdates) {
        startLocationUpdates();
    }
}

private void startLocationUpdates() {
    fusedLocationClient.requestLocationUpdates(locationRequest,
            locationCallback,
            Looper.getMainLooper());
}

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

กำหนดการเรียกกลับการอัปเดตตำแหน่ง

ผู้ให้บริการตำแหน่งที่ผสานจะเรียกใช้เมธอด Callback ของ LocationCallback.onLocationResult() อาร์กิวเมนต์ขาเข้ามีออบเจ็กต์รายการ Location ที่มีละติจูดและลองจิจูดของตำแหน่ง ข้อมูลโค้ดต่อไปนี้แสดงวิธีใช้LocationCallback อินเทอร์เฟซและกำหนดเมธอด จากนั้นรับการประทับเวลาของการอัปเดตตำแหน่ง และแสดงละติจูด ลองจิจูด และการประทับเวลาในอินเทอร์เฟซผู้ใช้ของแอป

Kotlin

private lateinit var locationCallback: LocationCallback

// ...

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

    locationCallback = object : LocationCallback() {
        override fun onLocationResult(locationResult: LocationResult?) {
            locationResult ?: return
            for (location in locationResult.locations){
                // Update UI with location data
                // ...
            }
        }
    }
}

Java

private LocationCallback locationCallback;

// ...

@Override
protected void onCreate(Bundle savedInstanceState) {
    // ...

    locationCallback = new LocationCallback() {
        @Override
        public void onLocationResult(LocationResult locationResult) {
            if (locationResult == null) {
                return;
            }
            for (Location location : locationResult.getLocations()) {
                // Update UI with location data
                // ...
            }
        }
    };
}

หยุดการอัปเดตตำแหน่ง

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

หากต้องการหยุดการอัปเดตตำแหน่ง ให้เรียกใช้ removeLocationUpdates() โดยส่ง LocationCallback ไปให้ ดังที่แสดงในตัวอย่างโค้ดต่อไปนี้

Kotlin

override fun onPause() {
    super.onPause()
    stopLocationUpdates()
}

private fun stopLocationUpdates() {
    fusedLocationClient.removeLocationUpdates(locationCallback)
}

Java

@Override
protected void onPause() {
    super.onPause();
    stopLocationUpdates();
}

private void stopLocationUpdates() {
    fusedLocationClient.removeLocationUpdates(locationCallback);
}

ใช้บูลีน requestingLocationUpdates เพื่อติดตามว่าขณะนี้การอัปเดตตำแหน่งเปิดอยู่หรือไม่ ในเมธอด onResume() ของกิจกรรม ให้ตรวจสอบว่าขณะนี้การอัปเดตตำแหน่งทำงานอยู่หรือไม่ และเปิดใช้งานหากไม่ได้ทำงานอยู่ โดยทำดังนี้

Kotlin

override fun onResume() {
    super.onResume()
    if (requestingLocationUpdates) startLocationUpdates()
}

Java

@Override
protected void onResume() {
    super.onResume();
    if (requestingLocationUpdates) {
        startLocationUpdates();
    }
}

บันทึกสถานะของกิจกรรม

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

ตัวอย่างโค้ดต่อไปนี้แสดงวิธีใช้ Callback onSaveInstanceState() ของกิจกรรมเพื่อบันทึกสถานะอินสแตนซ์

Kotlin

override fun onSaveInstanceState(outState: Bundle?) {
    outState?.putBoolean(REQUESTING_LOCATION_UPDATES_KEY, requestingLocationUpdates)
    super.onSaveInstanceState(outState)
}

Java

@Override
protected void onSaveInstanceState(Bundle outState) {
    outState.putBoolean(REQUESTING_LOCATION_UPDATES_KEY,
            requestingLocationUpdates);
    // ...
    super.onSaveInstanceState(outState);
}

กำหนดเมธอด updateValuesFromBundle() เพื่อกู้คืนค่าที่บันทึกไว้จากอินสแตนซ์ก่อนหน้าของกิจกรรม หากมี เรียกใช้เมธอดจากเมธอด onCreate() ของกิจกรรม ดังที่แสดงในตัวอย่างโค้ดต่อไปนี้

Kotlin

override fun onCreate(savedInstanceState: Bundle?) {
    // ...
    updateValuesFromBundle(savedInstanceState)
}

private fun updateValuesFromBundle(savedInstanceState: Bundle?) {
    savedInstanceState ?: return

    // Update the value of requestingLocationUpdates from the Bundle.
    if (savedInstanceState.keySet().contains(REQUESTING_LOCATION_UPDATES_KEY)) {
        requestingLocationUpdates = savedInstanceState.getBoolean(
                REQUESTING_LOCATION_UPDATES_KEY)
    }

    // ...

    // Update UI to match restored state
    updateUI()
}

Java

@Override
public void onCreate(Bundle savedInstanceState) {
    // ...
    updateValuesFromBundle(savedInstanceState);
}

private void updateValuesFromBundle(Bundle savedInstanceState) {
    if (savedInstanceState == null) {
        return;
    }

    // Update the value of requestingLocationUpdates from the Bundle.
    if (savedInstanceState.keySet().contains(REQUESTING_LOCATION_UPDATES_KEY)) {
        requestingLocationUpdates = savedInstanceState.getBoolean(
                REQUESTING_LOCATION_UPDATES_KEY);
    }

    // ...

    // Update UI to match restored state
    updateUI();
}

ดูข้อมูลเพิ่มเติมเกี่ยวกับการบันทึกสถานะอินสแตนซ์ได้ที่ข้อมูลอ้างอิงคลาสกิจกรรม Android

หมายเหตุ: หากต้องการพื้นที่เก็บข้อมูลถาวรมากขึ้น คุณสามารถจัดเก็บค่ากำหนดของผู้ใช้ไว้ใน SharedPreferences ของแอป ตั้งค่ากำหนดที่แชร์ในเมธอด onPause() ของกิจกรรม และเรียกข้อมูลค่ากำหนดใน onResume() ดูข้อมูลเพิ่มเติมเกี่ยวกับการบันทึกค่ากําหนดได้ที่หัวข้อการบันทึกชุดคีย์-ค่า

แหล่งข้อมูลเพิ่มเติม

หากต้องการดูข้อมูลเพิ่มเติม โปรดใช้ประโยชน์จากแหล่งข้อมูลต่อไปนี้

ตัวอย่าง