১. শুরু করার আগে
এই কোডল্যাবটি আপনাকে একটি সহজ অ্যান্ড্রয়েড অ্যাপ তৈরি করতে শেখাবে, যা গুগল ম্যাপস প্ল্যাটফর্ম নেভিগেশন এসডিকে ব্যবহার করে আগে থেকে কনফিগার করা কোনো গন্তব্যে নেভিগেট করতে পারে।
কাজ শেষ হলে আপনার অ্যাপটি দেখতে এইরকম হবে।

পূর্বশর্ত
- কোটলিনে বেসিক অ্যান্ড্রয়েড অ্যাপ ডেভেলপমেন্টের জ্ঞান
- গুগল ম্যাপস এসডিকে-র মৌলিক ধারণা, যেমন—ম্যাপ, অবস্থান, স্থানাঙ্ক ইত্যাদির সাথে কিছুটা পরিচিতি থাকা প্রয়োজন।
আপনি যা শিখবেন
- কীভাবে নেভিগেশন এসডিকে ব্যবহার করে কোনো গন্তব্যে নেভিগেট করার জন্য একটি সহজ অ্যান্ড্রয়েড অ্যাপ তৈরি করা যায়।
- রিমোট গুগল ম্যাভেন রিপোজিটরি থেকে নেভিগেশন এসডিকে কীভাবে ইন্টিগ্রেট করবেন
- নেভিগেশন এসডিকে এন্ড ইউজার টার্মস ব্যবহার করে লোকেশন পারমিশন এবং ইউজার এগ্রিমেন্ট কীভাবে ম্যানেজ করবেন
- SDK কীভাবে শুরু করবেন
- কীভাবে গন্তব্য নির্ধারণ করবেন এবং নেভিগেশন নির্দেশনা শুরু করবেন
আপনার যা যা লাগবে
- অ্যান্ড্রয়েড স্টুডিও-র সর্বশেষ স্থিতিশীল সংস্করণ ইনস্টল করা আছে। এই কোডল্যাবটি অ্যান্ড্রয়েড স্টুডিও জেলিফিশ ব্যবহার করে তৈরি করা হয়েছে। আপনি যদি ভিন্ন কোনো সংস্করণ ব্যবহার করেন, তাহলে ইন্টারফেস এবং কম্পোনেন্টগুলোর চেহারা ও বিন্যাস ভিন্ন হতে পারে।
- বিলিং চালু থাকা একটি গুগল অ্যাকাউন্ট এবং প্রজেক্ট।
- ইউএসবি ডিবাগিং সক্ষম করা ডেভেলপার মোডে থাকা একটি অ্যান্ড্রয়েড ডিভাইস, অথবা একটি অ্যান্ড্রয়েড এমুলেটর। আপনি যেটিই বেছে নিন না কেন, সেটিকে অবশ্যই নেভিগেশন এসডিকে-এর ন্যূনতম প্রয়োজনীয়তা পূরণ করতে হবে।
২. প্রস্তুত হন
আপনার যদি আগে থেকে একটি Google Cloud Platform অ্যাকাউন্ট এবং বিলিং চালু করা কোনো প্রজেক্ট না থাকে, তাহলে https://developers.google.com/maps/gmp-get-started-এ দেওয়া 'Getting started with Google Maps Platform' নির্দেশাবলী অনুসরণ করে আপনার Google Cloud প্রজেক্টটি সেট আপ করুন।
কনসোলে আপনার গুগল ক্লাউড প্রজেক্টটি নির্বাচন করুন।
ক্লাউড কনসোলে , প্রজেক্ট ড্রপ-ডাউন মেনুতে ক্লিক করুন এবং এই কোডল্যাবের জন্য যে প্রজেক্টটি ব্যবহার করতে চান সেটি নির্বাচন করুন।

আপনার প্রোজেক্টে নেভিগেশন SDK সক্রিয় করুন
এই কোডল্যাবের জন্য প্রয়োজনীয় গুগল ম্যাপস প্ল্যাটফর্ম এপিআই এবং এসডিকে-গুলো গুগল ক্লাউড মার্কেটপ্লেস থেকে সক্রিয় করুন।
Google Cloud Console-এ APIs & Services > Library-তে যান এবং "Navigation SDK" অনুসন্ধান করুন।
আপনি একটি অনুসন্ধানের ফলাফল দেখতে পাবেন।

প্রোডাক্ট ডিটেইলস পেজটি খুলতে নেভিগেশন এসডিকে রেজাল্টে ক্লিক করুন। আপনার প্রোজেক্টে এসডিকে-টি সক্রিয় করতে এনাবল বাটনে ক্লিক করুন।
অ্যান্ড্রয়েডের জন্য গুগল ম্যাপস এসডিকে-এর ক্ষেত্রেও এই প্রক্রিয়াটি পুনরাবৃত্তি করুন।
একটি এপিআই কী তৈরি করুন
ক্লাউড কনসোলের ক্রেডেনশিয়ালস পেজ থেকে একটি এপিআই কী তৈরি করুন। আপনি "গুগল ম্যাপস প্ল্যাটফর্মের সাথে শুরু করা" এর কুইকস্টার্ট বিভাগের ৩ নম্বর ধাপের নির্দেশাবলী অনুসরণ করতে পারেন। গুগল ম্যাপস প্ল্যাটফর্মে করা সমস্ত অনুরোধের জন্য একটি এপিআই কী প্রয়োজন।
৩. নমুনা প্রজেক্ট ফাইলগুলো সংগ্রহ করুন।
এই অংশে বর্ণনা করা হয়েছে, কীভাবে এই কোডল্যাবের জন্য গিটহাব রিপোজিটরি থেকে ফাইল ক্লোন করে একটি সাধারণ খালি অ্যান্ড্রয়েড স্টুডিও প্রজেক্ট তৈরি করতে হয়। গিটহাব রিপোটিতে কোডল্যাব কোডের আগের এবং পরের সংস্করণ রয়েছে। কোডল্যাবটি একটি খালি প্রজেক্ট টেমপ্লেট দিয়ে শুরু হবে এবং ধীরে ধীরে সম্পূর্ণ অবস্থায় পৌঁছাবে। কোথাও আটকে গেলে আপনি রেফারেন্স হিসেবে রিপোটিতে থাকা সম্পূর্ণ প্রজেক্টটি ব্যবহার করতে পারেন।
এই কোডল্যাবের কোড পেতে এই গিটহাব রিপোটি ক্লোন করুন।
git clone https://github.com/googlemaps-samples/codelab-navigation-101-android-kotlin.git
আপনার কম্পিউটারে গিট ইনস্টল করা না থাকলে, কোডটি পেতে এই বাটনটিতে ক্লিক করুন:
আপনাকে যত দ্রুত সম্ভব কাজ শুরু করতে সাহায্য করার জন্য, রিপোটির Starter ফোল্ডারে কিছু স্টার্টার কোড রয়েছে যা আপনাকে এই কোডল্যাবটি অনুসরণ করতে সাহায্য করবে। স্টার্টার প্রজেক্টটিতে একটি বেসিক অ্যাপ UI এবং বিল্ড কনফিগারেশন রয়েছে, কিন্তু এতে নেভিগেশন SDK যোগ করা নেই। এছাড়াও একটি সম্পূর্ণ Solution প্রজেক্ট রয়েছে, যদি আপনি যেকোনো সময় এগিয়ে যেতে বা আপনার কাজের অগ্রগতি পরীক্ষা করতে চান।
অ্যান্ড্রয়েড স্টুডিওতে ক্লোন করা রিপোটি খুলুন।
একবার আপনি রিপোটি স্থানীয়ভাবে ক্লোন করে নিলে, অ্যান্ড্রয়েড স্টুডিও ব্যবহার করে Starter ফোল্ডারটি একটি বিদ্যমান প্রজেক্ট হিসেবে খুলুন।
- "Welcome to Android Studio" ডায়ালগ বক্স থেকে, "Open" বোতামটিতে ক্লিক করুন।
- আপনি যে ফোল্ডারে ক্লোন করা রিপোটি সেভ করেছেন সেখানে যান এবং টপ লেভেলের "
codelab-navigation-101-android-kotlin" ফোল্ডারের ভিতরে থাকাStarterফোল্ডারটি সিলেক্ট করুন। - প্রজেক্টটি বিল্ড ও রান হচ্ছে কিনা তা যাচাই করুন।
একটি ভার্চুয়াল ডিভাইস যোগ করুন, অথবা একটি হার্ডওয়্যার ডিভাইস সংযুক্ত করুন
আপনার কম্পিউটারের সাথে একটি অ্যান্ড্রয়েড ডিভাইস সংযোগ করতে, অ্যান্ড্রয়েড স্টুডিও-তে দেওয়া হার্ডওয়্যার ডিভাইসে অ্যাপ চালানোর নির্দেশাবলী অনুসরণ করুন। বিকল্পভাবে, আপনি অ্যান্ড্রয়েড ভার্চুয়াল ডিভাইস (AVD) ম্যানেজার ব্যবহার করে একটি ভার্চুয়াল ডিভাইস কনফিগার করতে পারেন। এমুলেটর বেছে নেওয়ার সময়, নিশ্চিত করুন যে আপনি এমন একটি ইমেজ বেছে নিয়েছেন যাতে গুগল এপিআই (Google APIs) অন্তর্ভুক্ত রয়েছে।
অ্যান্ড্রয়েড স্টুডিওতে, রান মেনু অপশন বা প্লে বাটন আইকনে ক্লিক করুন। নির্দেশ অনুযায়ী একটি ডিভাইস বেছে নিন।
৪. আপনার অ্যাপে নেভিগেশন এসডিকে যোগ করুন
আপনার প্রজেক্টে নেভিগেশন SDK লাইব্রেরি এবং আপনার API কী যোগ করুন।
আপনার অ্যাপে নেভিগেশন এসডিকে লাইব্রেরি যোগ করতে, আপনাকে আপনার অ্যাপ-লেভেলের build.gradle.kts পরিবর্তন করে গুগল ম্যাভেন রিপোজিটরি থেকে নেভিগেশন এসডিকে ফেচ করতে হবে এবং একটি ভার্সন নম্বর কনফিগার করতে হবে।
আপনার বিল্ড কনফিগে নেভিগেশন এসডিকে ভার্সন নম্বরটি সংরক্ষণ করার জন্য একটি ভেরিয়েবল তৈরি করুন।
আপনার অ্যাপে ব্যবহৃত নেভিগেশন এসডিকে-র ভার্সনের মান রাখার জন্য অ্যাপ-লেভেলের build.gradle.kts ফাইলে একটি ভ্যারিয়েবল সেট করুন, যাতে ভবিষ্যতে সহজেই সর্বশেষ ভার্সনে পরিবর্তন করা যায়।
সর্বশেষ সংস্করণ নম্বর জানতে নেভিগেশন এসডিকে রিলিজ নোট দেখুন।
val navSdkVersion by extra("6.0.0")
আপনি ফাইল > প্রজেক্ট স্ট্রাকচার > ভেরিয়েবলস-এ থাকা ডায়ালগ বক্সটি ব্যবহার করে এই এবং অন্যান্য ভেরিয়েবলের মানও পরিবর্তন করতে পারেন:

বিল্ড কনফিগারেশনে একটি নির্ভরতা যোগ করুন
এখন আপনার অ্যাপ-লেভেলের build.gradle.kts. ব্যবহৃত ভার্সনটি হবে ${navSdkVersion} এর মান, যা আপনি এইমাত্র আপনার অ্যাপ-লেভেলের build.gradle.kts ফাইলে সেট করেছেন:
dependencies {
// Include the Google Navigation SDK.
api("com.google.android.libraries.navigation:navigation:${navSdkVersion}")
...
আপনার এপিআই কী যোগ করুন
এপিআই কী পরিচালনা করতে সিক্রেটস গ্রেডল প্লাগইন ব্যবহার করুন।
আপনার অ্যাপে এপিআই কী (API key) নিরাপদে পরিচালনা করার জন্য আমরা সিক্রেটস গ্রেডল প্লাগইন (Secrets Gradle plugin) ব্যবহার করার পরামর্শ দিই। প্লাগইনটি আপনার টপ লেভেল build.gradle.kts ফাইলে একটি ডিপেন্ডেন্সি হিসেবে প্রাথমিক প্রজেক্ট টেমপ্লেটে যোগ করা হয়েছে।
// Top-level build file where you can add configuration options common to all sub-projects/modules.
plugins {
id("com.google.android.libraries.mapsplatform.secrets-gradle-plugin") version "2.0.1" apply false
//... other plugin definitions here
}
আপনার টপ-লেভেল ডিরেক্টরিতে থাকা secrets.properties ফাইলটি খুলুন এবং তারপর YOUR_API_KEY এর জায়গায় আপনার API কী বসান। আপনার কী-টি এই ফাইলে সংরক্ষণ করুন, কারণ secrets.properties ফাইলটি কোনো ভার্সন কন্ট্রোল সিস্টেমে চেক-ইন করার যোগ্য নয়।
MAPS_API_KEY=YOUR_API_KEY
এই বিষয়ে আরও তথ্যের জন্য, নেভিগেশন এসডিকে ডকুমেন্টেশনে আপনার অ্যাপে এপিআই কী যোগ করুন (Add the API key to your app) অংশটি দেখুন।
local.defaults.properties-এর বিষয়বস্তু যাচাই করুন।
খালি প্রজেক্টটিতেও আপনার টপ-লেভেল ডিরেক্টরিতে একটি local.defaults.properties ফাইল রয়েছে, যা secrets.properties ফাইলটির ফোল্ডারেই অবস্থিত। এটি খুলুন এবং নিম্নলিখিত কোডটি পর্যবেক্ষণ করুন।
MAPS_API_KEY=DEFAULT_API_KEY
প্রজেক্টে secrets.properties ফাইলটি যোগ করা না থাকলে MAPS_API_KEY প্রপার্টির জন্য একটি ব্যাকআপ ভ্যালু প্রদান করতে এটি রাখা হয়েছে, যাতে বিল্ড ব্যর্থ না হয়। এই ফাইলটি সম্পাদনা করার কোনো প্রয়োজন নেই। যদি secrets.properties ফাইলে MAPS_API_KEY এর সংজ্ঞা খুঁজে না পাওয়া যায়, তাহলে ডিফল্ট ভ্যালুটি রানটাইমে একটি API কী এরর দেখিয়ে অ্যাপটিকে বন্ধ করে দেবে।
অ্যান্ড্রয়েড ম্যানিফেস্টটি আপনার নির্দিষ্ট করা এপিআই কী ব্যবহার করছে কিনা তা যাচাই করুন।
app/src/main/AndroidManifest.xml ফাইলটি খুলুন। আপনি লক্ষ্য করবেন যে অ্যাপ্লিকেশনটির জন্য এপিআই কী (API key) সেট করতে MAPS_API_KEY প্রপার্টিটি ব্যবহৃত হয়:
<meta-data
android:name="com.google.android.geo.API_KEY"
android:value="${MAPS_API_KEY}" />
আপনার অ্যাপ-লেভেলের build.gradle.kts ফাইলটি খুলুন এবং secrets প্রপার্টিটি খুঁজুন।
প্লাগইনের propertiesFileName সেটিংটি secrets.properties এ সেট করতে হবে এবং defaultPropertiesFileName মান local.defaults.properties হতে হবে।
secrets {
// Optionally specify a different file name containing your secrets.
// The plugin defaults to "local.properties"
propertiesFileName = "secrets.properties"
// A properties file containing default secret values. This file can be
// checked in version control.
defaultPropertiesFileName = "local.defaults.properties"
}
সমস্ত ফাইল সংরক্ষণ করুন এবং গ্রেডলের সাথে আপনার প্রজেক্ট সিঙ্ক করুন।
৫. অ্যাপের অনুমতি কনফিগার করুন এবং একটি সাধারণ UI যোগ করুন।
সুনির্দিষ্ট অবস্থানের অনুমতির জন্য অনুরোধ করুন
নেভিগেশন এসডিকে কাজ করার জন্য জিপিএস সিগন্যালের উপর নির্ভর করে, তাই আপনার অ্যাপকে ব্যবহারকারীর কাছে সুনির্দিষ্ট অবস্থানের ডেটা অ্যাক্সেস করার অনুমতি চাইতে হবে। AndroidManifest.xml-এর <manifest> এলিমেন্টের চাইল্ড হিসেবে সুনির্দিষ্ট অবস্থান অ্যাক্সেস করার অনুমতিটি যোগ করুন।
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools" >
<uses-permission
android:name="android.permission.ACCESS_FINE_LOCATION"
/>
</manifest>
আপনি অ্যান্ড্রয়েড ডেভেলপার ডকুমেন্টেশনের 'লোকেশন পারমিশনের জন্য অনুরোধ' বিভাগে অ্যান্ড্রয়েড লোকেশন পারমিশন সম্পর্কে আরও পড়তে পারেন।
আপনার অ্যাপটি একটি অ্যান্ড্রয়েড ১৪ ডিভাইসে চালানোর জন্য, সুনির্দিষ্ট অবস্থান অ্যাক্সেস অনুমতির স্থানে নিম্নলিখিত uses-permission ট্যাগটি যোগ করে ফোরগ্রাউন্ড সার্ভিস লোকেশন অনুমতির জন্য অনুরোধ করুন:
<uses-permission android:name="android.permission.FOREGROUND_SERVICE_LOCATION" />
সাধারণ UI সহ একটি লঞ্চ অ্যাক্টিভিটি যোগ করুন
আপনার অ্যাপটি চালু হওয়ার সময়, স্টার্ট-আপের সময় এমন কোডের প্রয়োজন হবে যা ব্যবহারকারী তার অবস্থান অ্যাক্সেস করার অনুমতি দিয়েছেন কিনা তা পরীক্ষা করবে এবং প্রতিটি সম্ভাব্য পরিস্থিতি সামাল দেবে; অনুমতি না দেওয়া হয়ে থাকলে, অনুমতির জন্য অনুরোধ করবে। এটি করার জন্য, আপনার অ্যাপে একটি সাধারণ ইউজার ইন্টারফেস (UI) যোগ করুন। এই কোডল্যাবটিতে অ্যান্ড্রয়েড স্টুডিওতে একটি নতুন, খালি 'ভিউস' অ্যাক্টিভিটি তৈরি করার সময় যে UI তৈরি হয়, সেটি ব্যবহার করা হয়েছে। নেভিগেশন UI-এর জন্য অ্যাক্টিভিটিতে কোড যোগ করার আগে, অবস্থানের অনুমতি পরীক্ষা করার জন্য আপনাকে এটি পরিবর্তন করে নিতে হবে।
কোড এডিটরে MainActivity.kt ফাইলটি খুলুন এবং কোডটি পরিদর্শন করুন, যেখানে একটি সাধারণ UI দেখা যাচ্ছে।
রানটাইমে অবস্থান অ্যাক্সেসের অনুমতির জন্য অনুরোধ করুন
নেভিগেশন এসডিকে চালু হওয়ার আগেই আপনার অ্যাপকে সুনির্দিষ্ট অবস্থান অ্যাক্সেস করার জন্য অনুরোধটি পাঠাতে হবে।
আপনার অ্যাপ চালু হওয়ার সময় এই চেকটি নিশ্চিত করতে, আপনার Activity-র ওভাররাইড করা onCreate() মেথডের মধ্যে MainActivity ক্লাসে কিছু কোড যোগ করুন।
নিম্নলিখিত কোডটি যাচাই করে দেখে যে ব্যবহারকারী ফাইন লোকেশনের অনুমতি দিয়েছেন কিনা। যদি না দিয়ে থাকেন, তবে এটি অনুমতির জন্য অনুরোধ করে। এই কোডটি আপনার onCreate() মেথডের ভিতরে যোগ করুন।
val permissions =
if (VERSION.SDK_INT >= VERSION_CODES.TIRAMISU) {
arrayOf(permission.ACCESS_FINE_LOCATION, permission.POST_NOTIFICATIONS)
} else {
arrayOf(permission.ACCESS_FINE_LOCATION)
}
if (permissions.any { !checkPermissionGranted(it) }) {
if (permissions.any { shouldShowRequestPermissionRationale(it) }) {
// Display a dialogue explaining the required permissions.
}
val permissionsLauncher =
registerForActivityResult(
RequestMultiplePermissions(),
{ permissionResults ->
if (permissionResults.getOrDefault(permission.ACCESS_FINE_LOCATION, false)) {
onLocationPermissionGranted()
} else {
finish()
}
},
)
permissionsLauncher.launch(permissions)
} else {
android.os.Handler(Looper.getMainLooper()).postDelayed({ onLocationPermissionGranted() }, SPLASH_SCREEN_DELAY_MILLIS)
}
}
private fun checkPermissionGranted(permissionToCheck: String): Boolean =
ContextCompat.checkSelfPermission(this, permissionToCheck) == PackageManager.PERMISSION_GRANTED
আপনার MainActivity ক্লাসে onLocationPermissionGranted নামে একটি নতুন ফাংশন যোগ করুন, যা ব্যবহারকারী তাদের অবস্থান শেয়ার করার অনুমতি দিলে তার ফলাফল পরিচালনা করবে। পরবর্তী ধাপগুলোতে আমরা একটি নতুন নেভিগেশন অ্যাক্টিভিটি চালু করার জন্য এখানে কোড যোগ করব।
private fun onLocationPermissionGranted() {
//code to initialize Navigation SDK will go here
}
আপনার প্রজেক্টটি বিল্ড করুন। বিল্ডে কোনো ত্রুটি থাকলে, সেগুলো খুঁজে বের করে সমাধান করুন।
আপনার প্রজেক্টটি একটি নতুন ভার্চুয়াল ডিভাইসে চালান। অ্যাপটি ইনস্টল ও চালু হওয়ার সময় আপনি অনুমতির অনুরোধের ডায়ালগ বক্সটি দেখতে পাবেন।
৬. একটি নেভিগেশন ইউজার ইন্টারফেস যোগ করুন
নেভিগেশন UI যোগ করার দুটি উপায় আছে: SupportNavigationFragment অথবা NavigationView ।
সরলতার জন্য কোডল্যাবটিতে একটি NavigationView ব্যবহার করা হয়েছে।
লেআউট সম্পাদনা করুন
NavigationView-এর জন্য একটি লেআউট যোগ করতে res/layout/activity_main.xml সম্পাদনা করুন।
- ফাইলটি খুলুন এবং কোড ভিউতে যান।
- নিচের উদাহরণের মতো করে ফাইলটির সম্পূর্ণ বিষয়বস্তু একটি
RelativeLayoutভেতরে একটিNavigationViewএর নতুন লেআউট দিয়ে প্রতিস্থাপন করুন। যেহেতু আপনি অ্যাপটিতে শুধু একটি নেভিগেশন ভিউ যোগ করবেন, তাই একটি সাধারণ লেআউটই যথেষ্ট হবে। - আপনার NavigationView-কে "
@+id/navigation_view" আইডিটি দিন।
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
<com.google.android.libraries.navigation.NavigationView
android:id="@+id/navigation_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
/>
</RelativeLayout>
নেভিগেশন কার্যকলাপ সেট আপ করুন
অ্যান্ড্রয়েড স্টুডিওতে, এডিটরে MainActivity.kt ফাইলটি খুলুন।
আপনার অ্যাপে নেভিগেশন অভিজ্ঞতা সঠিকভাবে কাজ করছে কিনা তা নিশ্চিত করতে কিছু প্রাথমিক সেটআপ কোড যোগ করুন। MainActivity.kt ফাইলে নিম্নলিখিত পরিবর্তনগুলি করুন:
- আপনার
NavigationViewরেফারেন্স করার জন্য আপনারMainActivityক্লাসে একটি ভেরিয়েবল ডিক্লেয়ার করুন:
private lateinit var navView: NavigationView
- আপনার
NavigationViewএর একটি রেফারেন্স পেতেonCreate()মেথডে কিছু কোড যোগ করুন:
navView = findViewById(R.id.navigation_view)
navView.onCreate(savedInstanceState)
- নেভিগেশন নির্দেশনার সময় স্ক্রিনটি যেন চালু থাকে, তা নিশ্চিত করতে
onCreate()মেথডে কিছু কোড যোগ করুন:
// Ensure the screen stays on during nav.
window.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON)
-
ViewCompat.setOnApplyWindowInsetsListenerকল করা কোডটি সম্পাদনা করে আপনারNavigationViewএর আইডি উল্লেখ করুন।
ViewCompat.setOnApplyWindowInsetsListener(findViewById(R.id.navigation_view)) { v, insets ->
val systemBars = insets.getInsets(WindowInsetsCompat.Type.systemBars())
v.setPadding(systemBars.left, systemBars.top, systemBars.right, systemBars.bottom)
insets
}
- ব্যবহারকারীকে প্রতিক্রিয়া দেখানোর জন্য ক্লাসে একটি
showToast()মেথড যোগ করুন:
private fun showToast(errorMessage: String) {
Toast.makeText(this@MainActivity, errorMessage, Toast.LENGTH_LONG).show()
}
৭. নেভিগেশন এসডিকে চালু করুন
এখন যেহেতু আপনি বেসিক নেভিগেশন অ্যাক্টিভিটি সেটআপ সম্পন্ন করেছেন, আপনি নেভিগেশন SDK ইনিশিয়ালাইজ করতে পারেন। এটি করার জন্য, আপনার MainActivity.kt ফাইলে নিম্নলিখিত কোডটি যোগ করুন:
/** Starts the Navigation API, capturing a reference when ready. */
@SuppressLint("MissingPermission")
private fun initializeNavigationApi() {
NavigationApi.getNavigator(
this,
object : NavigatorListener {
override fun onNavigatorReady(navigator: Navigator) {
// store a reference to the Navigator object
mNavigator = navigator
// code to start guidance will go here
}
override fun onError(@NavigationApi.ErrorCode errorCode: Int) {
when (errorCode) {
NavigationApi.ErrorCode.NOT_AUTHORIZED -> {
// Note: If this message is displayed, you may need to check that
// your API_KEY is specified correctly in AndroidManifest.xml
// and is been enabled to access the Navigation API
showToast(
"Error loading Navigation API: Your API key is " +
"invalid or not authorized to use Navigation."
)
}
NavigationApi.ErrorCode.TERMS_NOT_ACCEPTED -> {
showToast(
"Error loading Navigation API: User did not " +
"accept the Navigation Terms of Use."
)
}
else -> showToast("Error loading Navigation API: $errorCode")
}
}
},
)
}
এই কোডটি initializeNavigationApi() নামে একটি নতুন মেথড তৈরি করে। এই মেথডটি NavigationApi.getNavigator() কল করে একটি Navigator অবজেক্টের রেফারেন্স নেয় এবং কলব্যাকটি হ্যান্ডেল করার জন্য একটি NavigatorListener ইমপ্লিমেন্ট করে।
লক্ষ্য করুন যে, নেভিগেশন এপিআই ইনিশিয়ালাইজ করার সময় NavigationListener.onNavigatorReady মেথডটি কল করা হবে এবং প্যারামিটার হিসেবে একটি Navigator অবজেক্ট পাস করা হবে। উপরের কোডটি এই মেথডে পাস করা ইনিশিয়ালাইজ করা Navigator অবজেক্টটি দিয়ে আপনার পূর্বে ডিক্লেয়ার করা mNavigator ভ্যারিয়েবলটি আপডেট করবে।
অবশেষে, onLocationPermissionGranted মেথড থেকে আপনার initializeNavigationApi মেথডটিকে কল করার ব্যবস্থা যোগ করুন।
private fun onLocationPermissionGranted() {
initializeNavigationApi()
}
৮. গুরুত্বপূর্ণ নেভিগেশন ইভেন্টগুলির জন্য লিসেনার যোগ করুন
যখন আপনার ব্যবহারকারীরা নির্দেশনা অনুসরণ করেন, তখন নেভিগেশন SDK এমন ইভেন্ট চালু করবে যা পথিমধ্যে গুরুত্বপূর্ণ অবস্থার পরিবর্তন সম্পর্কে অ্যাপকে অবহিত করতে পারে, যেমন যখন ব্যবহারকারী পথ পরিবর্তন করেন বা তার গন্তব্যে পৌঁছান। MainActivity.kt ফাইলে, এই ইভেন্টগুলি পরিচালনা করার জন্য লিসেনার যোগ করুন:
-
MainActivityক্লাসের মধ্যে, ইভেন্ট লিসেনার অবজেক্টগুলোকে নির্দেশ করার জন্য দুটি ভেরিয়েবল ঘোষণা করুন:
private var arrivalListener: Navigator.ArrivalListener? = null
private var routeChangedListener: Navigator.RouteChangedListener? = null
- Navigator ইনিশিয়ালাইজ করার সময় লিসেনারগুলো সেট আপ করার জন্য একটি
registerNavigationListeners()মেথড যোগ করুন। Arrival ইভেন্টটি ফায়ার হলে এই মেথডটিNavigator.clearDestinations()মেথডকে কল করেNavigationViewকে রিসেট করে:
/**
* Registers a number of example event listeners that show an on screen message when certain
* navigation events occur (e.g. the driver's route changes or the destination is reached).
*/
private fun registerNavigationListeners() {
withNavigatorAsync {
arrivalListener =
Navigator.ArrivalListener { // Show an onscreen message
showToast("User has arrived at the destination!")
mNavigator?.clearDestinations()
}
mNavigator?.addArrivalListener(arrivalListener)
routeChangedListener =
Navigator.RouteChangedListener { // Show an onscreen message when the route changes
showToast("onRouteChanged: the driver's route changed")
}
mNavigator?.addRouteChangedListener(routeChangedListener)
}
}
-
initializeNavigationApiমেথডেরonNavigatorReadyকলব্যাক কোড থেকেregisterNavigationListeners()কলটি যোগ করুন:
override fun onNavigatorReady(navigator: Navigator) {
// store a reference to the Navigator object
mNavigator = navigator
//listen for events en route
registerNavigationListeners()
}
- ইউজার ইন্টারফেস কনফিগার করুন। গাইডেন্স চালু থাকা অবস্থায় আপনি নেভিগেশন ইউজার ইন্টারফেসের বিভিন্ন দিক নিয়ন্ত্রণ করতে পারেন। একটি গুরুত্বপূর্ণ কাস্টমাইজেশন হলো ক্যামেরার অবস্থান।
onNavigatorReadyতে রিটার্ন করাnavigatorঅবজেক্টেরsetTaskRemovedBehaviourমেথডটিতে নিম্নরূপভাবে একটি কল যোগ করুন। অ্যাপটি সোয়াইপ করে সরিয়ে দেওয়া হলে এটি গাইডেন্স এবং নোটিফিকেশন বন্ধ করে দেবে:
// Disables the guidance notifications and shuts down the app and background service
// when the user dismisses/swipes away the app from Android's recent tasks.
navigator.setTaskRemovedBehavior(Navigator.TaskRemovedBehavior.QUIT_SERVICE)
- একটি
CameraPerspectiveনির্দিষ্ট করার জন্যGoogleMap.followMyLocationএ একটি কল যোগ করুন।GoogleMapটি নিম্নলিখিতভাবেNavigatorView.getMapAsync()পদ্ধতির মাধ্যমে অ্যাক্সেস করা হয়:
navView.getMapAsync {
googleMap ->
googleMap.followMyLocation(GoogleMap.CameraPerspective.TILTED)
}
- অ্যাপের জীবনচক্র জুড়ে নেভিগেশন যেন মসৃণভাবে কাজ করে, তা নিশ্চিত করতে আপনার
MainActivityক্লাসে নিম্নলিখিত মেথডগুলো প্রয়োগ করুন:
override fun onSaveInstanceState(savedInstanceState: Bundle) {
super.onSaveInstanceState(savedInstanceState)
navView.onSaveInstanceState(savedInstanceState)
}
override fun onTrimMemory(level: Int) {
super.onTrimMemory(level)
navView.onTrimMemory(level)
}
override fun onStart() {
super.onStart()
navView.onStart()
}
override fun onResume() {
super.onResume()
navView.onResume()
}
override fun onPause() {
navView.onPause()
super.onPause()
}
override fun onConfigurationChanged(configuration: Configuration) {
super.onConfigurationChanged(configuration)
navView.onConfigurationChanged(configuration)
}
override fun onStop() {
navView.onStop()
super.onStop()
}
override fun onDestroy() {
navView.onDestroy()
withNavigatorAsync {
// Unregister event listeners to avoid memory leaks.
if (arrivalListener != null) {
navigator.removeArrivalListener(arrivalListener)
}
if (routeChangedListener != null) {
navigator.removeRouteChangedListener(routeChangedListener)
}
navigator.simulator?.unsetUserLocation()
navigator.cleanup()
}
super.onDestroy()
}
৯. একটি গন্তব্য নির্ধারণ করুন।
আপনি এখন একটি গন্তব্য নির্ধারণ করতে এবং নেভিগেশন নির্দেশনা শুরু করতে প্রস্তুত। MainActivity.kt ফাইলে নিম্নলিখিত পরিবর্তনগুলি করুন:
- একটি নতুন
navigateToPlace()মেথড যোগ করুন যা নেভিগেশন গন্তব্য নির্ধারণ করে এবং একটিplaceIdপ্যারামিটার গ্রহণ করে।
/**
* Requests directions from the user's current location to a specific place (provided by the
* Place ID).
*/
private fun navigateToPlace(placeId: String) {
}
- আপনার
navigateToPlace()মেথডে, মেথডটিতে পাস করা Place ID থেকে একটিWaypointতৈরি করতেWaypoint.builder()মেথডটি ব্যবহার করুন। Place ID-টি কোনো সুনির্দিষ্ট ঠিকানায় পরিণত না হলে, এর ফলে যেUnsupportedPlaceIdExceptionথ্রো হতে পারে, তা হ্যান্ডেল করুন:
val waypoint: Waypoint? =
// Set a destination by using a Place ID (the recommended method)
try {
Waypoint.builder().setPlaceIdString(placeId).build()
} catch (e: Waypoint.UnsupportedPlaceIdException) {
showToast("Place ID was unsupported.")
return
}
- ওয়েপয়েন্ট ব্যবহার করে গন্তব্য নির্ধারণ করতে আপনার
navigateToPlace()মেথডে নিম্নলিখিত কোডটি যোগ করুন:
val pendingRoute = mNavigator?.setDestination(waypoint)
// Set an action to perform when a route is determined to the destination
pendingRoute?.setOnResultListener { code ->
when (code) {
RouteStatus.OK -> {
// Code to start guidance will go here
}
RouteStatus.ROUTE_CANCELED -> showToast("Route guidance canceled.")
RouteStatus.NO_ROUTE_FOUND,
RouteStatus.NETWORK_ERROR ->
// TODO: Add logic to handle when a route could not be determined
showToast("Error starting guidance: $code")
else -> showToast("Error starting guidance: $code")
}
}
Navigator অবজেক্টের একটি setDestinations() মেথড আছে যা বিভিন্ন প্যারামিটার গ্রহণ করতে পারে। সবচেয়ে সাধারণ বিকল্পটি হলো একটি Waypoint সরবরাহ করা। এটি ডিফল্টভাবে DRIVING ভ্রমণ মোড ব্যবহার করবে, যা চার চাকার গাড়ির জন্য উপযুক্ত। setDestinations() মেথডটি একটি ListenableResultFuture অবজেক্ট রিটার্ন করে, যার মধ্যে একটি RouteStatus অবজেক্ট থাকে। RouteStatus টি নির্দেশ করবে গন্তব্যে পৌঁছানোর জন্য কোনো রুট পাওয়া গেছে কি না এবং যদি না পাওয়া যায়, তবে এটি আপনাকে বিভিন্ন ত্রুটিপূর্ণ অবস্থা সামাল দেওয়ার সুযোগ দেবে।
- নেভিগেশন ব্যবহারকারীর অভিজ্ঞতা উন্নত করতে অতিরিক্ত কনফিগারেশন পরিবর্তন করুন:
// Hide the toolbar to maximize the navigation UI
supportActionBar?.hide()
// Enable voice audio guidance (through the device speaker)
mNavigator?.setAudioGuidance(Navigator.AudioGuidance.VOICE_ALERTS_AND_GUIDANCE)
// Simulate vehicle progress along the route (for demo/debug builds)
if (BuildConfig.DEBUG) {
mNavigator?.simulator?.simulateLocationsAlongExistingRoute(
SimulationOptions().speedMultiplier(5f)
)
}
এই পরিবর্তনগুলোর মধ্যে নিম্নলিখিত উন্নতিগুলো অন্তর্ভুক্ত রয়েছে:
- নেভিগেশন UI-এর জন্য জায়গা সর্বাধিক করতে অ্যাকশন বারটি লুকানো হচ্ছে।
- সতর্কবার্তা এবং দিকনির্দেশনা জানানোর জন্য অডিও গাইডেন্স চালু করা।
- স্পিড মাল্টিপ্লায়ার নির্দিষ্ট করে ডিবাগিংয়ের জন্য সিমুলেটর সেট আপ করা।
- এমন একটি প্লেস আইডি (Place ID) খুঁজুন যা আপনার গন্তব্যস্থল হিসেবে কাজ করবে। আদর্শগতভাবে, এটি ব্যবহারকারীর অবস্থান থেকে খুব বেশি দূরে হওয়া উচিত নয়। গুগল ম্যাপস প্ল্যাটফর্মের প্লেস আইডি ফাইন্ডার ইউটিলিটি ব্যবহার করুন অথবা প্লেসেস এপিআই (Places API) কলের মাধ্যমে একটি প্লেস আইডি সংগ্রহ করুন।
আপনি যদি নেভিগেশন সিমুলেট করেন, তাহলে কোডের মাধ্যমে ব্যবহারকারীর অবস্থান নির্ধারণ করতে পারেন অথবা আপনার সংযুক্ত ডিভাইস থেকে তা নিতে পারেন। কোডল্যাবটি ধরে নেবে যে আপনি যুক্তরাজ্যের লন্ডনে একটি অবস্থান সিমুলেট করছেন।
- আপনার
MainActivityক্লাসে একটি শুরুর স্থান এবং একটি স্থানের আইডি সংরক্ষণ করার জন্য একটি কম্প্যানিয়ন অবজেক্ট যোগ করুন। এই কোডল্যাবে শুরুর স্থান হিসেবে লন্ডন এবং স্থানের আইডি হিসেবে ট্রাফালগার স্কোয়ার ব্যবহার করা হবে:
companion object{
const val TRAFALGAR_SQUARE ="ChIJH-tBOc4EdkgRJ8aJ8P1CUxo" //London, UK
val startLocation = LatLng(51.345678, -0.1234456)
}
-
initializeNavigationApiমেথডের ভিতরেonNavigatorReadyকলব্যাক থেকে আপনারnavigateToPlace()মেথডটিকে কল করুন, এবং এমন একটি লজিক শাখা যোগ করুন যা ডিবাগ মোডে এক্সিকিউট হবে এবং ব্যবহারকারীর অবস্থান সেট করবে:
// Disables the guidance notifications and shuts down the app and background service
// when the user dismisses/swipes away the app from Android's recent tasks.
navigator.setTaskRemovedBehavior(Navigator.TaskRemovedBehavior.QUIT_SERVICE)
mNavigator = navigator
if (BuildConfig.DEBUG) {
mNavigator?.simulator?.setUserLocation(MainActivity.startLocation)
}
//listen for events en route
registerNavigationListeners()
navView.getMapAsync {
googleMap ->
googleMap.followMyLocation(GoogleMap.CameraPerspective.TILTED)
}
//navigate to a destination
navigateToPlace(MainActivity.TRAFALGAR_SQUARE)
১০. আপনার কোড বিল্ড এবং রান করুন
প্রথমবার অ্যাপটি চালানোর সময়, আপনাকে অ্যাপটিকে অবস্থানের অনুমতি দিতে হবে এবং নেভিগেশন এসডিকে ব্যবহারের শর্তাবলী মেনে নিতে হবে।
দ্রষ্টব্য: অ্যাপটি চালালে setDestinations() মেথডটি কল হবে, যার ফলে প্রথম ১০০০টি গন্তব্য ব্যবহারের পর চার্জ প্রযোজ্য হবে। আরও তথ্যের জন্য ব্যবহার ও বিলিং দেখুন।


অবস্থান নির্ধারণ করা
ডিফল্টরূপে এমুলেটেড ডিভাইসটির অবস্থান ক্যালিফোর্নিয়ার মাউন্টেন ভিউতে অবস্থিত গুগল ক্যাম্পাসে সেট করা থাকতে পারে, যদি না আপনি কোডে বা এমুলেটর প্রোপার্টিজ ডায়ালগ ব্যবহার করে কোনো অবস্থান সেট করে থাকেন।
যদি তাই হয়, তাহলে আপনি দেখতে পারেন যে অ্যাপটি আপনার কনফিগার করা প্লেস আইডি-তে (ডিফল্টরূপে, সিডনি অপেরা হাউস, সিডনি, অস্ট্রেলিয়া) যাওয়ার কোনো রুট খুঁজে পাচ্ছে না। আপনার showToast() মেথড দ্বারা প্রদর্শিত "কোনো রুট পাওয়া যায়নি" লেখা একটি বার্তার মাধ্যমে এটি নির্দেশিত হবে।

শুরুর অবস্থান হার্ড কোড করা
কোডে একটি ভিন্ন অবস্থান সেট করতে, আপনার MainActivity.kt-এর navigateToPlace() মেথডে, mNavigator.startGuidance() কল করার আগে নিম্নলিখিত লাইনটি যোগ করুন:
mNavigator?.simulator?.setUserLocation(startLocation)
আপনার পছন্দের একটি ডিফল্ট অবস্থানে এমুলেটরটি চালু করা হচ্ছে।
ডিভাইস এমুলেটরে একটি ভিন্ন অবস্থান সেট করতে, এমুলেটরটি যদি আগে থেকে চালু না থাকে তবে সেটি চালু করুন এবং "এক্সটেন্ডেড কন্ট্রোলস" টুলটিপ সহ ৩ ডট মেনুতে ক্লিক করুন। যে ডায়ালগটি খুলবে, সেখানে "লোকেশন" এর জন্য একটি মেনু অপশন থাকবে।
উদাহরণস্বরূপ, আপনি যদি গন্তব্য হিসেবে সিডনি অপেরা হাউসের প্লেস আইডি ব্যবহার করেন, তাহলে অস্ট্রেলিয়ার সিডনিতে একটি স্থান বেছে নিন। যেমন, "বন্ডি বিচ" লিখে সার্চ করুন, একটি সাজেশন বেছে নিন এবং ডায়ালগের নিচের ডানদিকে থাকা "সেভ লোকেশন" বাটনে ক্লিক করুন। ভবিষ্যতে ব্যবহারের জন্য স্থানটিকে একটি সংরক্ষিত তালিকায় যুক্ত করতে আপনি "সেভ পয়েন্ট" বাটনেও ক্লিক করতে পারেন।

গন্তব্য হিসেবে যদি আপনি একটি ভিন্ন প্লেস আইডি সেট করেন, তাহলে এর কাছাকাছি একটি স্থান বেছে নিন, যাতে সিমুলেটেড রুটটি বাস্তবসম্মত হয় এবং সহজে ডিবাগ করার জন্য খুব বেশি দীর্ঘ না হয়।
অ্যাপটি পুনরায় চালু করুন, তাহলে এটি এখন গন্তব্যে চলে যাবে।

১১. অভিনন্দন!
আপনি এই কোডল্যাবটি সম্পন্ন করেছেন। খুব ভালো - আপনি আপনার গন্তব্যে পৌঁছে গেছেন! হ্যাপি কোডিং :-)

১২. এটিকে আরও এগিয়ে নিয়ে যাওয়া
আপনি যদি আপনার অ্যাপ ডেভেলপমেন্টকে আরও এগিয়ে নিয়ে যেতে চান, তাহলে অনুপ্রেরণার জন্য নিম্নলিখিত বিষয়গুলো দেখে নিতে পারেন।
- আরও নেভিগেশন ইভেন্টের জন্য নজর রাখুন । ড্রাইভার পথ পরিবর্তন করলে, অথবা গন্তব্যে পৌঁছালে একটি বার্তা দেখানোর জন্য কোড যোগ করুন।
- নেভিগেশন ইন্টারফেসটি কাস্টমাইজ করুন ।
- আপনি যদি আরও বড় কোনো চ্যালেঞ্জ নিতে চান, তাহলে ব্যবহারকারীকে গন্তব্য নির্ধারণের সুযোগ দিতে একটি প্লেসেস এপিআই প্লেস পিকার কন্ট্রোল যোগ করার চেষ্টা করুন। ইঙ্গিত: গিটহাবে থাকা নেভিগেশন এসডিকে ডেমো অ্যাপগুলোতে এর একটি নমুনা বাস্তবায়ন রয়েছে।
- গিটহাবে থাকা নেভিগেশন এসডিকে ডেমো অ্যাপগুলোতে ব্যবহৃত পদ্ধতি অবলম্বন করে অ্যাসিঙ্ক্রোনাসভাবে Navigator এবং GoogleMap অবজেক্ট কল করার ক্ষেত্রে সম্ভাব্য সমস্যাগুলো প্রতিরোধ করুন। আরও জটিল অ্যাপের ক্ষেত্রে, আপনার কোড চলার সময় এই অবজেক্টগুলোর ইনিশিয়ালাইজেশন সম্পূর্ণ নাও হতে পারে। পরামর্শ: খুব দ্রুত বাস্তবায়নের জন্য আপনি আপনার MainActivity.kt ফাইলের শেষে InitializedNavScope ক্লাসটি যোগ করতে পারেন।