مکان یابی در اندروید توسط GoogleApi

آموزش مکان یابی GPS در برنامه نویسی اندروید توسط GoogleApi

قابلیت مکان یابی در ابزارهای هوشمند و بخصوص دستگاه‌های اندرویدی شامل موبایل و تبلت، به یکی از پرکاربردترین امکانات این ابزار بدل شده و در طیف گسترده‌ای از برنامه‌ها و به تناسب سرویسی که به کاربران ارائه می‌دهند، این قابلیت پیاده سازی شده است.
اپلیکیشن‌های حمل و نقل شامل درخواست تاکسی و پیک، فروشگاه‌های آنلاین و برنامه‌های مسیریاب نمونه‌هایی از کاربرد قابلیت مکان‌یابی کاربر را نشان می‌دهد. در این برنامه‌ها، موقعیت مکانی کاربر دریافت شده و متناسب با ماهیت و کاربرد برنامه، پردازش مربوطه انجام می‌پذیرد.
در این جلسه قصد دارم نحوه پیاده سازی قابلیت مکان یابی در اندروید توسط FusedLocationProviderClient را آموزش دهم که از زیرمجموعه‌های GoogleApi محسوب می‌شود.

این بخش شامل مباحث زیر می‌باشد:

  • معرفی API مکان یابی گوگل با نام Fused location provider
  • تعریف مجوز دسترسی به موقعیت مکانی در مانیفست پروژه
  • استفاده از کلاس LocationRequest جهت ارسال درخواست مکان یابی در اندروید به همراه تنظیمات مدنظر
  • استفاده از LocationSettingsRequest.Builder برای بیلد کردن تنظیمات درخواست
  • دریافت پاسخ موقعیت مکانی توسط LocationCallback
  • نحوه فعال و غیر فعال کردن دکمه‌ها
  • نحوه استفاده از آیتم‌های مکان یابی در اندروید مانند GPS، WiFi و شبکه موبایل
  • بررسی همخوانی امکانات مکان یابی دستگاه با آنچه برنامه ما نیاز دارد توسط SettingsClient
  • تعیین مدت فاصله زمانی بین بروزرسانی‌های موقعیت مکانی
  • نمایش دیالوگ فعالسازی قابلیت Location در صورت خاموش بودن آن
  • توقف دریافت و بروزرسانی موقعیت مکانی توسط removeLocationUpdates
  • توقف عملیات بروزرسانی موقعیت مکانی هنگام توقف اکتیویتی جهت کاهش مصرف انرژی

تصاویر نهایی پروژه:

نمایش طول و عرض جغرافیایی در اکتیویتی
مکان یابی و بروزرسانی آن توسط API گوگل در اندروید
نمایش دیالوگ فعالسازی قابلیت مکان یابی
دریافت مجوز دسترسی به موقعیت مکانی از کاربر

 

این جلسه در قالب PDF و در ۳۴ صفحه تهیه شده که در ادامه چند صفحه‌ ابتدایی را مشاهده می‌کنید:

قابلیت مکان یابی در اندروید

برای مکان یابی در سیستم عامل اندروید نیاز به انجام کار پیچیده و نوشتن کدهای طولانی نداریم. به لطف گوگل، در Google Play services یک Location API با نام Fused location provider در دسترس توسعه دهندگان قرار داده شده که با پیاده سازی آن در اپلیکیشن، می‌توان آخرین موقعیت مکانی کاربر را بدست آورد و از آن درون برنامه استفاده کرد.
این API از داده‌های دریافتی از GPS (جی پی اس) و همچنین سایر آیتم‌هایی که برای تعیین موقعیت مکانی کاربر استفاده می‌شود مانند Wi-Fi و شبکه موبایل، اطلاعات مربوط به وضعیت فعلی دستگاه را دریافت کرده و مختصات آن را در دسترس برنامه‌هایی قرار می‌دهد که به این اطلاعات نیاز دارند. ضمن اینکه مختصات دائما بروز شده و می‌توانیم در فواصل مشخصی، مختصات جدید موقعیت دستگاه را مرتبا دریافت کنیم.

نکته: همانطور که اشاره شد، این API به Google Play services وابسته است لذا در دستگاه‌هایی که این سرویس نصب یا فعال نباشد، امکان مکان یابی فراهم نیست. برای مثال در شبیه ساز Genymotion باید Open Gapps روی دیوایس فعال شده باشد.

برای دریافت موقعیت مکانی کاربر به واسطه Google Play services لازم است از کلاس FusedLocationProviderClient در پروژه خود استفاده کنیم.
در این جلسه یک پروژه ساده را ایجاد می‌کنیم که با فعال شدن قابلیت مکان یابی در اندروید، به طور مستمر و هر ۱۰ ثانیه یکبار مختصات موقعیت مکانی دستگاه را نمایش می‌دهد.

پروژه نمایش موقعیت جغرافیایی در اندروید

قصد دارم یک پروژه ساده را تمرین و بررسی کنیم که دو Button و سه TextView در اکتیویتی تعریف شده است. با کلیک روی دکمه نخست، قابلیت مکان یابی دستگاه اندرویدی فعال شده و مختصات دریافتی و همچنین زمان آخرین بروزرسانی در TextView ها نمایش داده می‌شود. همچنین با کلیک روی دکمه دوم، قابلیت مکان یابی غیر فعال خواهد شد.
طبق مبحث آموزش ساخت پروژه در اندروید استودیو یک پروژه اندرویدی با نام Location می‌سازم. اکتیویتی را از نوع Empty Activity و زبان را Java انتخاب کردم.
در ابتدای مبحث عنوان شد که ابزار مورد استفاده ما یکی از Location API های Google Play services هست. بنابراین در قدم اول لازم است کتابخانه موردنیاز این API را به پروژه اضافه کنیم:

build.gradle(app)

apply plugin: 'com.android.application'

android {
    compileSdkVersion 30
    buildToolsVersion "30.0.0"

    defaultConfig {
        applicationId "ir.android_studio.location"
        minSdkVersion 19
        targetSdkVersion 30
        versionCode 1
        versionName "1.0"

        testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
    }

    buildTypes {
        release {
            minifyEnabled false
            proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
        }
    }
}

dependencies {
    implementation fileTree(dir: "libs", include: ["*.jar"])
    implementation 'androidx.appcompat:appcompat:1.1.0'
    implementation 'com.google.android.gms:play-services-location:17.0.0'
}

کتابخانه com.google.android.gms:play-services-location همانطور که از نامش پیداست برای استفاده از قابلیت location در Play services ساخته شده.
مسلما برنامه ما برای دریافت موقعیت مکانی، نیاز به دریافت مجوز حق دسترسی یا Permission مربوطه از سیستم عامل را دارد. قبلا در مبحث آموزش Runtime Permission در اندروید با انواع مجوزها آشنا شدیم. برای دسترسی برنامه به موقعیت مکانی، مجوز زیر را درون مانیفست پروژه تعریف می‌کنم:

<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>

همچنین از آنجایی که قصد داریم از قابلیت مکان یابی در اندروید به واسطه API موجود در Google Play services دستگاه استفاده کنیم، باید مشخص شود برنامه با چه نسخه‌ای از ابزار Google Play services موجود در SDK اندروید استودیو ساخته شده است. تگ meta-data زیر را به بدنه تگ application مانیفست اضافه می‌کنیم:

<meta-data android:name="com.google.android.gms.version"
    android:value="@integer/google_play_services_version" />

در انتها، مانیفست پروژه به صورت زیر تکمیل می‌شود:

AndroidManifest.xml

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="ir.android_studio.location">

    <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>

    <application
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/AppTheme">

        <meta-data android:name="com.google.android.gms.version"
            android:value="@integer/google_play_services_version" />

        <activity android:name=".MainActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
    </application>

</manifest>

در مرحله بعد، آیتم‌های مورد نیاز در layout اکتیویتی را اضافه می‌کنم که شامل دو Button و سه TextView است:

activity_main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    tools:context=".MainActivity">

    <Button
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="شروع مکان یابی"
        android:textSize="20dp"
        android:id="@+id/start_btn"
        android:onClick="startUpdatesButtonHandler"/>

    <Button
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:text="توقف مکان یابی"
        android:textSize="20dp"
        android:id="@+id/stop_btn"
        android:onClick="stopUpdatesButtonHandler"
        android:enabled="false"/>

    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:id="@+id/latitude_txt"
        android:gravity="center"
        android:textSize="20dp" />

    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:id="@+id/longitude_txt"
        android:gravity="center"
        android:textSize="20dp"/>

    <TextView
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:id="@+id/update_txt"
        android:gravity="center"
        android:textSize="20dp"/>

</LinearLayout>

دو ویژگی جدید به نام‌های onClick و enabled در دکمه‌ها استفاده شده. ویژگی اول برای تعریف متد مربوط به رویداد دکمه در اکتیویتی است که جایگزین setOnClickListener بشمار می‌رود. مورد دوم هم چنانچه با مقدار false تعریف شود، دکمه در حالت پیش فرض به صورت غیر فعال و غیر قابل کلیک ظاهر می‌شود.
کارکرد پروژه ما به اینصورت است که با کلیک روی دکمه اول، ابتدا بررسی می‌شود آیا پرمیشن Location قبلا به برنامه ما داده شده یا نه. بعد از دریافت مجوز دسترسی از کاربر، در صورتی که قابلیت مکان یابی دستگاه فعال بوده و موقعیت جغرافیایی آن در دسترس باشد، اطلاعات آن شامل Latitude (عرض جغرافیایی)، Longitude (طول جغرافیایی) و همچنین آخرین زمان دریافت آخرین موقعیت در قالب سه TextView نمایش داده می‌شود. قبلا در آموزش نمایش نقشه Google Map در برنامه اندرویدی با این اصطلاحات آشنا شدیم.
همچنین در صورت کلیک روی دکمه دوم، عملیات بروزرسانی موقعیت مکانی متوقف خواهد شد. البته چنانچه قابلیت مکان یابی فعال نباشد ابتدا یک دیالوگ به کاربر نمایش داده می‌شود و اعلام می‌کند این برنامه به فعال شدن Location نیاز دارد که با تایید آن توسط کاربر، این قابلیت فعال خواهد شد.
حالا نوبت به نوشتن کدهای back end اکتیویتی می‌رسد. در قدم اول، MainActivity پروژه را به صورت زیر تکمیل کردم که جزئیات را به مرور توضیح خواهم داد:

MainActivity.java

package ir.android_studio.location;

import androidx.appcompat.app.AppCompatActivity;

import android.location.Location;
import android.os.Bundle;
import android.widget.Button;
import android.widget.TextView;

import com.google.android.gms.location.FusedLocationProviderClient;
import com.google.android.gms.location.LocationCallback;
import com.google.android.gms.location.LocationRequest;
import com.google.android.gms.location.LocationSettingsRequest;
import com.google.android.gms.location.SettingsClient;

public class MainActivity extends AppCompatActivity {

    private Button startBtn, stopBtn;
    private TextView latitudeTxt, longitudeTxt, updateTimeTxt;

    private static final int REQUEST_PERMISSIONS_REQUEST_CODE = 2;
    private static final int REQUEST_CHECK_SETTINGS = 1;
    private static final long UPDATE_INTERVAL_IN_MILLISECONDS = 10000;
    private static final long FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS = 5000;
    private final static String KEY_REQUESTING_LOCATION_UPDATES = "requesting-location-updates";
    private final static String KEY_LOCATION = "location";
    private final static String KEY_LAST_UPDATED_TIME_STRING = "last-updated-time-string";
    private Boolean requestingLocationUpdates;
    private String lastUpdateTime;

    private FusedLocationProviderClient mFusedLocationClient;
    private SettingsClient settingsClient;
    private LocationRequest locationRequest;
    private LocationSettingsRequest locationSettingsRequest;
    private LocationCallback locationCallback;
    private Location currentLocation;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);

        startBtn = findViewById(R.id.start_btn);
        stopBtn = findViewById(R.id.stop_btn);
        latitudeTxt = findViewById(R.id.latitude_txt);
        longitudeTxt = findViewById(R.id.longitude_txt);
        updateTimeTxt = findViewById(R.id.update_txt);

        requestingLocationUpdates = false;
        lastUpdateTime = "";

       mFusedLocationClient = LocationServices.getFusedLocationProviderClient(this);
       settingsClient = LocationServices.getSettingsClient(this);


    }
}

همانطور که ملاحظه می‌کنید ابتدا دکمه‌ و TextView ها را تعریف کرده‌ام.
همچنین چندین متغیر از جنس int، long، String و Boolean و در نهایت، از ۶ کلاس که مربوط به کتابخانه play-services-location هستند یک نمونه ساخته‌ام.
در ابتدا برای متغیر requestingLocationUpdates درون متد onCreate مقدار false تعریف کردم زیرا در حالت عادی و تا قبل از کلیک روی دکمه شروع مکان یابی نباید موقعیت مکانی دریافت و بروزرسانی شود. برای متغیری که جهت نمایش آخرین تاریخ بروزرسانی موقعیت تعریف شده هم یک رشته خالی به عنوان مقدار پیش فرض تعریف شده.
در پایان با استفاده از دو متد getFusedLocationProviderClient و getSettingsClient دو کلاس FusedLocationProviderClient و SettingsClient آماده استفاده در اکتیویتی شده‌اند.

ارسال درخواستِ دریافت موقعیت مکانی:

برای ارسال درخواست دریافت موقعیت مکانی به API و همچنین تعیین فاصله زمانی بروزرسانی آن، از کلاس LocationRequest استفاده می‌کنیم. یک متد با نام دلخواه createLocationRequest به اکتیویتی اضافه کرده و داخل آن را به صورت زیر تکمیل می‌کنم:

private void createLocationRequest() {

    locationRequest = new LocationRequest();
    locationRequest.setInterval(UPDATE_INTERVAL_IN_MILLISECONDS);
    locationRequest.setFastestInterval(FASTEST_UPDATE_INTERVAL_IN_MILLISECONDS);
    locationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);

}

در کد فوق ابتدا از کلاس LocationRequest یک نمونه با نام locationRequest ساخته شده. سپس ۳ متد از این کلاس تعریف و مقدار دهی شده است.
setInterval: به وسیله این متد، فاصله زمانی بروزرسانی موقعیت مکانی را تعیین می‌کنیم که بر حسب میلی ثانیه تعریف می‌شود. من برای متغیر UPDATE_INTERVAL_IN_MILLISECONDS که از جنس long تعریف شده، مقدار ۱۰۰۰۰ تعیین کردم بنابراین برنامه من هر ۱۰ ثانیه یکبار جدیدترین مختصات موقعیت مکانی را از سیستم عامل و به عبارت دیگر از Google Play services دریافت می‌کند.
setFastestInterval:: این متد، سریع‌ترین (Fastest) فاصله زمانی برای دریافت بروزرسانی موقعیت مکانی را تعیین می‌کند. کاربرد این متد این است که چنانچه در بازه زمانی کوتاهتری از آنچه قبلا در setInterval تعریف کردیم، موقعیت مکانی دستگاه به واسطه سایر برنامه‌های موجود روی دستگاه (مانند اپلیکیشن‌های مکان یاب و…) بروزرسانی شود، مختصات توسط برنامه ما نیز دریافت شده و ارسال درخواست بروزرسانی موقعیت مکانی از جانب برنامه ما به تعویق می‌افتد. این کار باعث کاهش تعداد درخواست‌های بروزرسانی از جانب برنامه‌های نصب شده روی دستگاه شده که در نهایت موجب صرفه جویی در مصرف باتری خواهد شد.
من برای این متد مقدار ۵۰۰۰ میلی ثانیه را تعیین کردم. بنابراین چنانچه بعد از آخرین درخواست بروزرسانی از جانب برنامه ما، یک درخواست بروزرسانی موقعیت مکانی در کمتر از مدت ۵ ثانیه از جانب برنامه دیگری به API ارسال شود، مختصات دریافتی توسط برنامه ما نیز دریافت شده و ارسال درخواست بعدی تا ۱۰ ثانیه دیگر به تعویق می‌افتد.
setPriority:: این متد همانطور که از نامش پیداست (Priority به معنی اولویت) اولویت درخواست مکان یابی ما را برای سیستم عامل مشخص می‌کند. این اولویت شامل نوع و دقت مکان یابی است که مشخص می‌کند در تعیین موقعیت از چه پارامترهایی استفاده و از چه آیتم‌های صرف نظر شود.

تعیین دقت مکان یابی Google Play services توسط متد setPriority

به عنوان مثال PRIORITY_HIGH_ACCURACY بیشترین دقت را در تعیین مکان بکار می‌گیرد که عمدتا از GPS برای تعیین موقعیت استفاده می‌شود و طبیعتا مصرف باتری نیز با افزایش همراه خواهد بود. اما در نوع دیگری مانند PRIORITY_BALANCED_POWER_ACCURACY عمدتا از اطلاعات دریافتی از شبکه WiFi و دکل‌های مخابراتی استفاده می‌شود که مصرف انرژی کمتری داشته و البته دقت آن نیز نسبت به GPS به مراتب پایین تر خواهد بود.
برای من دقت در اولویت است بنابراین PRIORITY_HIGH_ACCURACY را انتخاب کرده‌ام.

تعیین نوع سرویس‌های مکان یابی

در قسمت قبل، تنظیماتی که برای سرویس مکان یابی لازم بود را در locationRequest تعیین کردیم. برای ارسال این تنظیمات به API مکان یابی Google Play services باید از کلاس LocationSettingsRequest.Builder استفاده کنیم.
یک تابع جدید با نام دلخواه buildLocationSettingsRequest در اکتیویتی ایجاد کردم که به صورت زیر تکمیل شده:

private void buildLocationSettingsRequest() {

    LocationSettingsRequest.Builder lsrBuilder = new LocationSettingsRequest.Builder();
    lsrBuilder.addLocationRequest(locationRequest);
    locationSettingsRequest = lsrBuilder.build();

}

دریافت پاسخ موقعیت مکانی

درخواستی که در قسمت نخست و توسط کلاس LocationRequest به API ارسال شد، توسط کلاس LocationCallback دریافت می‌شود. یک متد دیگر با نام دلخواه createLocationCallback به اکتیویتی اضافه کرده و به صورت زیر تکمیل می‌کنم:

private void createLocationCallback() {

    locationCallback = new LocationCallback() {
        @Override
        public void onLocationResult(LocationResult locationResult) {
            super.onLocationResult(locationResult);
            
            currentLocation = locationResult.getLastLocation();
            lastUpdateTime = DateFormat.getTimeInstance().format(new Date());
            updateLocationUI();

        }
    };

}

ابتدا یک نمونه از کلاس LocationCallback ساخته‌ام. سپس متد onLocationResult را تعریف کرده‌ام:

دریافت موقعیت مکانی در اندروید توسط متد LocationCallback

این متد یک پارامتر از جنس LocationResult دارد که به صورت پیش فرض نام locationResult برای آن انتخاب شده است. این متد هنگامی فراخوانی می‌شود که موقعیت مکانی دستگاه در دسترس باشد.
داخل این متد، سه خط زیر اضافه شده:

currentLocation = locationResult.getLastLocation();
lastUpdateTime = DateFormat.getTimeInstance().format(new Date());
updateLocationUI();

currentLocation را قبلا داخل بدنه کلاس از جنس کلاس Location تعریف کردم. در اینجا آخرین موقعیت مکانی دستگاه توسط getLastLocation دریافت شده و در currentLocation ذخیره می‌شود.

نکته: همواره به نامگذاری متدها و کلاس‌ها دقت کنید. در اکثر موارد، صرفا با ترجمه نام می‌توانید به کاربرد آن پی ببرید. برای مثال get last location برابر با “دریافت آخرین موقعیت مکانی” و current location برابر با “موقعیت مکانی فعلی” است. یعنی ما آخرین موقعیت را از API دریافت کرده و در متغیری ذخیره می‌کنیم تا در برنامه خود از آن به عنوان موقعیت فعلی دستگاه استفاده کنیم.

در خط دوم، آخرین زمان بروزرسانی موقعیت مکانی در متغیر lastUpdateTime ذخیره می‌شود. عملیات بروزرسانی صفحه برنامه و نمایش مختصات جغرافیایی و همچنین تاریخ بروزرسانی را در یک متد مجزا انجام خواهیم داد که نام updateLocationUI را برای آن انتخاب کرده‌ام. در ادامه مبحث این متد را کامل خواهیم کرد.

تکمیل متد updateLocationUI

متد را به اینصورت تکمیل می‌کنم:

private void updateLocationUI() {

    if (currentLocation != null) {
        latitudeTxt.setText(String.format(Locale.ENGLISH,  "%s: %f", "عرض جغرافیایی", currentLocation.getLatitude()));
        longitudeTxt.setText(String.format(Locale.ENGLISH,  "%s: %f", "طول جغرافیایی", currentLocation.getLongitude()));
        updateTimeTxt.setText(String.format(Locale.ENGLISH,  "%s: %s", "آخرین بروزرسانی", lastUpdateTime));
    }

}

در اینجا بررسی می‌شود چنانچه currentLocation خالی نبود و به عبارتی، مختصات جغرافیایی را از API دریافت کرده باشد، به همراه زمان آخرین بروزرسانی موقعیت روی TextView های مربوطه نمایش داده شوند.

بروزرسانی داده‌های دریافتی روی صفحه

برای ذخیره و بروزرسانی مختصات و زمان آخرین بروزرسانی، ابتدا متد onSaveInstanceState را درون اکتیویتی اضافه کرده و تکمیل می‌کنم:

بروزرسانی موقعیت جغرافیایی دستگاه اندرویدی به واسطه onSaveInstanceState

@Override
public void onSaveInstanceState(@NonNull Bundle outState, @NonNull PersistableBundle outPersistentState) {

    outState.putBoolean(KEY_REQUESTING_LOCATION_UPDATES, requestingLocationUpdates);
    outState.putParcelable(KEY_LOCATION, currentLocation);
    outState.putString(KEY_LAST_UPDATED_TIME_STRING, lastUpdateTime);

    super.onSaveInstanceState(outState, outPersistentState);
}

در خط اول، یک مقدار از جنس Boolean یعنی true یا false در Bundle ذخیره می‌شود که مشخص می‌کند آیا درخواست بروزرسانی موقعیت ارسال شده یا خیر. همچنین در خط دوم موقعیت فعلی و در خط سوم، زمان بروزرسانی ذخیره می‌شود.
حالا برای فراخوانی داده‌های ذخیره شده در قسمت قبل و ارسال آنها به رابط کاربری، یک متد دیگر با نام دلخواه updateValuesFromBundle به اکتیویتی اضافه می‌کنم. این تابع یک پارامتر از جنس Bundle دارد که نام savedState را برای آن انتخاب کرده‌ام:

private void updateValuesFromBundle(Bundle savedState) {

    if (savedState != null) {
        if (savedState.containsKey(KEY_REQUESTING_LOCATION_UPDATES)) {
            requestingLocationUpdates = savedState.getBoolean(KEY_REQUESTING_LOCATION_UPDATES);
        }
        if (savedState.containsKey(KEY_LOCATION)) {
            currentLocation = savedState.getParcelable(KEY_LOCATION);
        }
        if (savedState.containsKey(KEY_LAST_UPDATED_TIME_STRING)) {
            lastUpdateTime = savedState.getString(KEY_LAST_UPDATED_TIME_STRING);
        }
        
        updateUI();
        
    }

}

ابتدا بررسی شده چنانچه savedState خالی نباشد (یعنی قبلا داده‌هایی در Bundle ذخیره شده باشد) سایر شروط را اجرا کن.
قبلا در متد onSaveInstanceState داده‌ها را با سه کلید ذخیره کردیم. اینجا Bundle بررسی می‌شود و چنانچه کلیدها وجود داشتند؛ یعنی saveState.containsKey(KEY_NAME) خالی نبود، مقدار آن را در متغیر مربوطه قرار بده. لغت contains به معنی “شامل بودن” است.
در قسمت قبل، داده‌ها ذخیره (Put) و در این قسمت، دریافت (Get) شده‌اند.
در نهایت، بروزرسانی داده‌ها توسط متد updateUI انجام خواهد شد که در ادامه مبحث توضیح خواهم داد.

جهت مطالعه ادامه آموزش، فایل PDF را دانلود نمائید

توجه : سورس پروژه درون پوشه Exercises قرار دارد

با توجه به اینکه آموزش‌های پایه با قیمت پایین در اختیار کاربر قرار گرفته و درآمد حاصل صرف تامین هزینه‌های وب سایت و تهیه آموزش‌های آتی می‌شود، به اشتراک گذاری این فایل با دیگران خلاف اخلاق است.

دانلود نسخه PDF این آموزش به همراه سورس پروژه
تعداد صفحات : ۳۴
حجم : ۲ مگابایت
قیمت : ۷۰۰۰ تومان
توجه: صرفا در صورتی از درگاه پشتیبان استفاده کنید که قادر به پرداخت از طریق سبد دانلود نباشید.
درگاه پشتیبان
این مطلب چقدر برایتان مفید بود؟ لطفا امتیاز دهید
دوره آموزش برنامه نویسی اندروید
دوره آموزش برنامه نویسی اندروید

آموزش‌ها در دو دسته «پایه» و «تکمیلی» منتشر می‌شوند.
آموزش‌های پایه شامل مباحث اصلی و آموزش‌های تکمیلی مطالبی است که می‌بایست در کنار مطالب اصلی از آنها استفاده کنیم.
شما با دریافت این دوره به تمامی آموزش‌های غیر رایگان و رایگان موجود در وب سایت دسترسی دارید که تخفیفی برای آموزش‌های غیر رایگان نیز درنظر گرفته شده. این پکیج به دو صورت دانلودی و ارسال پستی ارائه می‌گردد.
با خرید این دوره، به تمامی آموزش‌های غیر رایگانی که در آینده منتشر می‌شود نیز به صورت رایگان دسترسی خواهید داشت!

یک دیدگاه بنویسید

پرسش‌های زیر تایید و پاسخ داده نخواهد شد:
۱ : جزء موارد پاسخ داده شده در مطلب "مشکلات و پرسش های رایج" باشد
۲ : سوال قبلا توسط کاربران در دیدگاهها مطرح و پاسخ داده شده باشد
۳ : سوال خارج از مبحث آموزشی موجود در این صفحه باشد

دیدگاهتان را بنویسید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *

کد امنیتی *