External Services. CSE 5236: Mobile Application Development Course Coordinator: Dr. Rajiv Ramnath Instructor: Adam C. Champion

Similar documents
Android Programming วรเศรษฐ ส วรรณ ก.

Android Application Model I

Google Maps library requires v2.50 or above.

Android Application Model I. CSE 5236: Mobile Application Development Instructor: Adam C. Champion, Ph.D. Course Coordinator: Dr.

Lab 6: Google Maps Android API v2 Android Studio 10/14/2016

Programming with Android: The Google Maps Library. Slides taken from

Mobile Programming Lecture 7. Dialogs, Menus, and SharedPreferences

1. Location Services. 1.1 GPS Location. 1. Create the Android application with the following attributes. Application Name: MyLocation

Mobile Application Development MyRent Settings

User Interface Development. CSE 5236: Mobile Application Development Instructor: Adam C. Champion Course Coordinator: Dr.

IEMS 5722 Mobile Network Programming and Distributed Server Architecture

Hybrid Apps Combining HTML5 + JAVASCRIPT + ANDROID

RUNTIME PERMISSIONS IN ANDROID 6.0 Lecture 10a

Action Bar. (c) 2010 Haim Michael. All Rights Reserv ed.

Android Programs Day 5

Have a development environment in 256 or 255 Be familiar with the application lifecycle

Android permissions Defining and using permissions Component permissions and related APIs

UI Fragment.

Starting Another Activity Preferences

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

Q.1 Explain the dialog and also explain the Demonstrate working dialog in android.

Mobile Computing Fragments

Tutorial: Setup for Android Development

Fragments were added to the Android API in Honeycomb, API 11. The primary classes related to fragments are: android.app.fragment

DEPARTMENT OF COMPUTER SCIENCE THE UNIVERSITY OF HONG KONG. CSIS0801 Final Year Project. WhozzUp - A Novel Big Data App for HK (Individual Report)

05. RecyclerView and Styles

Real-Time Embedded Systems

Embedded Systems Programming - PA8001

CS 528 Mobile and Ubiquitous Computing Lecture 4a: Fragments, Camera Emmanuel Agu

Computer Science Large Practical: Storage, Settings and Layouts. Stephen Gilmore School of Informatics October 26, 2017

Our First Android Application

Tablets have larger displays than phones do They can support multiple UI panes / user behaviors at the same time

Diving into Android. By Jeroen Tietema. Jeroen Tietema,

COMP4521 EMBEDDED SYSTEMS SOFTWARE

Kotlin for wearables: use case. Andrey Mukamolov

MVC Apps Basic Widget Lifecycle Logging Debugging Dialogs

CMSC436: Fall 2013 Week 3 Lab

Produced by. Mobile Application Development. Higher Diploma in Science in Computer Science. Eamonn de Leastar

More Effective Layouts

LifeStreet Media Android Publisher SDK Integration Guide

API Guide for Gesture Recognition Engine. Version 2.0

Multiple devices. Use wrap_content and match_parent Use RelativeLayout/ConstraintLayout Use configuration qualifiers

Activities and Fragments

EMBEDDED SYSTEMS PROGRAMMING Application Tip: Saving State

Lecture 13 Mobile Programming. Google Maps Android API

Produced by. Mobile Application Development. Higher Diploma in Science in Computer Science. Eamonn de Leastar

The Internet. CS 2046 Mobile Application Development Fall Jeff Davidson CS 2046

Applied Cognitive Computing Fall 2016 Android Application + IBM Bluemix (Cloudant NoSQL DB)

Internal Services. CSE 5236: Mobile Application Development Instructor: Adam C. Champion, Ph.D. Course Coordinator: Dr.

Workshop. 1. Create a simple Intent (Page 1 2) Launch a Camera for Photo Taking

EMBEDDED SYSTEMS PROGRAMMING UI Specification: Approaches

Answers to Exercises

Addressing Non-Functional Requirements in Mobile Applications

Screen Slides. The Android Studio wizard adds a TextView to the fragment1.xml layout file and the necessary code to Fragment1.java.

Android. Mobile operating system developed by Google A complete stack. Based on the Linux kernel Open source under the Apache 2 license

This lecture. The BrowserIntent Example (cont d)

UNDERSTANDING ACTIVITIES

Mobila applikationer och trådlösa nät

CS 4330/5390: Mobile Application Development Exam 1

Android Coding. Dr. J.P.E. Hodgson. August 23, Dr. J.P.E. Hodgson () Android Coding August 23, / 27

CS 4518 Mobile and Ubiquitous Computing Lecture 5: Rotating Device, Saving Data, Intents and Fragments Emmanuel Agu

Multiple Activities. Many apps have multiple activities

Overview of Activities

Android Application Development using Kotlin

Mobile and Ubiquitous Computing: Android Programming (part 4)

Android Application Development

Produced by. Mobile Application Development. Eamonn de Leastar

Islamic University of Gaza. Faculty of Engineering. Computer Engineering Department. Mobile Computing ECOM Eng. Wafaa Audah.

EMBEDDED SYSTEMS PROGRAMMING Application Tip: Managing Screen Orientation

Android Application Model II. CSE 5236: Mobile Application Development Instructor: Adam C. Champion, Ph.D. Course Coordinator: Dr.

ANDROID APPS DEVELOPMENT FOR MOBILE AND TABLET DEVICE (LEVEL I)

Mobile and Ubiquitous Computing: Android Programming (part 3)

Produced by. Mobile Application Development. Higher Diploma in Science in Computer Science. Eamonn de Leastar

ANDROID APPS DEVELOPMENT FOR MOBILE AND TABLET DEVICE (LEVEL I)

Programming with Android: Geo-localization and Google Map Services. Luca Bedogni. Dipartimento di Scienze dell Informazione Università di Bologna

Mobile Programming Lecture 5. Composite Views, Activities, Intents and Filters

MAD ASSIGNMENT NO 3. Submitted by: Rehan Asghar BSSE AUGUST 25, SUBMITTED TO: SIR WAQAS ASGHAR Superior CS&IT Dept.

CS 528 Mobile and Ubiquitous Computing Lecture 3b: Android Activity Lifecycle and Intents Emmanuel Agu

South Africa Version Control.

ARCHETYPE MODERN ANDROID ARCHITECTURE STEPAN GONCHAROV / DENIS NEKLIUDOV

ActionBar. import android.support.v7.app.actionbaractivity; public class MyAppBarActivity extends ActionBarActivity { }

Meniu. Create a project:

LECTURE NOTES OF APPLICATION ACTIVITIES

Login with Amazon. Getting Started Guide for Android apps

Android Data Binding: This is the DSL you're looking for

ACTIVITY, FRAGMENT, NAVIGATION. Roberto Beraldi

Android Basics. Android UI Architecture. Android UI 1

Intents. Your first app assignment

Fragments and the Maps API

API Guide for Gesture Recognition Engine. Version 1.1

EMBEDDED SYSTEMS PROGRAMMING Application Basics

Create Parent Activity and pass its information to Child Activity using Intents.

Update to newest version and translate to English.

Writing Efficient Drive Apps for Android. Claudio Cherubino / Alain Vongsouvanh Google Drive Developer Relations

Produced by. Mobile Application Development. David Drohan Department of Computing & Mathematics Waterford Institute of Technology

Xin Pan. CSCI Fall

Produced by. Mobile Application Development. David Drohan Department of Computing & Mathematics Waterford Institute of Technology

Android Apps Development for Mobile and Tablet Device (Level I) Lesson 4. Workshop

Understand applications and their components. activity service broadcast receiver content provider intent AndroidManifest.xml

10.1 Introduction. Higher Level Processing. Word Recogniton Model. Text Output. Voice Signals. Spoken Words. Syntax, Semantics, Pragmatics

Transcription:

External Services CSE 5236: Mobile Application Development Course Coordinator: Dr. Rajiv Ramnath Instructor: Adam C. Champion 1

External Services Viewing websites Location- and map-based functionality REST-based Web services invocation 2

Invoking Browser App Java // HelpFragment.java private void launchbrowser( String url) { Uri theuri = Uri.parse(url); Intent LaunchBrowserIntent = new Intent(Intent.ACTION_VIEW, theuri); startactivity( LaunchBrowserIntent); Kotlin // HelpFragment.kt private fun launchbrowser( url: String) { val theuri = Uri.parse(url) val LaunchBrowserIntent = Intent(Intent.ACTION_VIEW, theuri) startactivity( LaunchBrowserIntent) URL: http://en.wikipedia.org/wiki/tictactoe Note: Activity stacking due to re-launch of browser on mobile page 3

Embedded WebView - Layout <?xml version="1.0" encoding="utf-8"?> <ScrollView...> <LinearLayout......> <WebView android:id="@+id/helpwithwebview" android:layout_width="match_parent" android:layout_height="200dip" android:layout_weight="1.0"/> <Button... android:text="exit"/> </LinearLayout> </ScrollView> 4

Embedded WebView: Java // HelpWebViewFragment.java public View oncreateview(...) { View v = inflater.inflate(r.layout.fragment_help_webview,...); WebView helpinwebview = (WebView) v.findviewbyid(r.id.helpwithwebview); mprogressbar = (ProgressBar) v.findviewbyid(r.id.webviewprogress); mprogressbar.setmax(100); View buttonexit = v.findviewbyid(r.id.button_exit); buttonexit.setonclicklistener(this); Bundle extras = getactivity().getintent().getextras(); if (extras!= null) { murl = extras.getstring(arg_uri); /*... */ //... helpinwebview.setwebviewclient(new WebViewClient() { public boolean shouldoverrideurlloading(...) { return false; ); helpinwebview.setwebchromeclient(new WebChromeClient() { public void onprogresschanged(webview webview, int progress) { if (progress == 100) { mprogressbar.setvisibility(view.gone); else { mprogressbar.setvisibility(view.visible); mprogressbar.setprogress(progress); ); helpinwebview.loadurl(murl); return v; 5

Embedded WebView: Kotlin // HelpWebViewFragment.kt override fun oncreateview(... ): View? { val v = inflater.inflate(r.layout.fragment_help_webview,...) val helpinwebview = v.findviewbyid<webview>(r.id.helpwithwebview) mprogressbar = v.findviewbyid<progressbar>(r.id.webviewprogress) mprogressbar.apply { max = 100 val buttonexit = v.findviewbyid<button>(r.id.button_exit) buttonexit.setonclicklistener(this) val extras = activity.intent.extras if (extras!= null) { murl = extras.getstring(arg_uri) WebView.setWebContentsDebuggingEnabled(true) helpinwebview.settings.javascriptenabled = true helpinwebview.webviewclient = object : WebViewClient() { override fun shouldoverrideurlloading(... ): Boolean { return false helpinwebview.webchromeclient = object : WebChromeClient() { override fun onprogresschanged(... ) { if (progress == 100) { mprogressbar.visibility = View.GONE else { mprogressbar.visibility = View.VISIBLE mprogressbar.progress = progress helpinwebview.loadurl(murl) return v 6

Location-Based Applications These mix-and-match the following actions: Opening a map Invoking a geocoding service on a point of interest Navigating the map to a position or make a mapbased calculation Determining the user s geolocation from the device (latitude, longitude) 7

Additional Requirements for Maps Use built-in GoogleMap with a FragmentActivity Link against Google APIs for Android (rather than standard Android SDK) Declare the use of the Google map package: <uses-library android:name="com.google.android.maps /> Request the appropriate permissions, e.g.: <uses-permission android:name="android.permission.internet"/> <uses-permission android:name="android.permission.access_network_state"/> <uses-permission android:name="android.permission.access_coarse_location"/> <uses-permission android:name="android.permission.access_fine_location"/> <uses-permission android:name="android.permission.write_external_storage"/> <uses-permission android:name="com.google.android.providers.gsf.permission.read_gservices /> Request a Map API key Goes in AndroidManifest.xml as <meta-data android:name="com.google.android.maps.v2.api_key android:value=... /> See https://developers.google.com/maps/documentation/android/start Need OpenGL ES v2: <uses-feature android:glesversion="0x00020000 8 android:required="true"/>

Map Fragment Layout <fragment xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:id="@+id/map" tools:context=".mapsactivity" android:name="com.google.android.gms.maps.supportmapfragment"/> Google Maps uses Fragments UI Fragment needs to be loaded dynamically 9

Map Fragment Code: Java (1) // MapsFragment.java public class MapsFragment extends SupportMapFragment implements OnMapReadyCallback { private GoogleMap mmap; private GoogleApiClient mapiclient; private static final String[] LOCATION_PERMISSIONS = new String[] { Manifest.permission.ACCESS_FINE_LOCATION, Manifest.permission.ACCESS_COARSE_LOCATION ; private FusedLocationProviderClient mfusedlocationproviderclient; private Location mlocation; private LatLng mdefaultlocation; private static final int REQUEST_LOCATION_PERMISSIONS = 0; private boolean mlocationpermissiongranted = false;... // MapsActivity.java just uses a SingleFragmentActivity 10

Map Fragment Code: Java (2) // MapsFragment.java (continued) public void oncreate(bundle savedinstancestate) { super.oncreate(savedinstancestate); sethasoptionsmenu(true); mapiclient = new GoogleApiClient.Builder(getActivity()).addApi(LocationServices.API).addConnectionCallbacks(new GoogleApiClient.ConnectionCallbacks() { public void onconnected(@nullable Bundle bundle) { getactivity().invalidateoptionsmenu(); public void onconnectionsuspended(int i) {... ).build(); getmapasync(this); public void onresume() { super.onresume(); setupeula(); findlocation(); 11

Map Fragment Code: Java (3) // MapsFragment.java (continued) public void onstart() { //... getactivity().invalidateoptionsmenu(); mapiclient.connect(); public void onstop() { //... mapiclient.disconnect(); private void findlocation() { updatelocationui(); if (haslocationpermission()) { mfusedlocationproviderclient = LocationServices.getFusedLocationProviderClient(getActivity()); mdefaultlocation = new LatLng(40.0, -83.0); LocationRequest locationrequest = LocationRequest.create(); locationrequest.setpriority(locationrequest.priority_high_accuracy); locationrequest.setnumupdates(1); locationrequest.setinterval(0); FusedLocationProviderClient locationprovider = LocationServices.getFusedLocationProviderClient(getActivity()); Task locationresult = locationprovider.getlastlocation(); locationresult.addoncompletelistener(getactivity(), new OnCompleteListener() { public void oncomplete(@nonnull Task task) { if (task.issuccessful()) { mlocation = (Location) task.getresult(); mmap.movecamera(cameraupdatefactory.newlatlngzoom(new LatLng(mLocation.getLatitude(), mlocation.getlongitude()), 16)); 12 else { /* Disable Location */ ); // Else request permissions, end of method.

Map Fragment Code: Java (4) // MapsFragment.java (continued) private void setupeula() { msettings = getactivity().getsharedpreferences(getstring(r.string.prefs), 0); boolean iseulaaccepted = msettings.getboolean(getstring(r.string.eula_accepted_key), false); if (!iseulaaccepted) { DialogFragment euladialogfragment = new EulaDialogFragment(); euladialogfragment.show(getactivity().getsupportfragmentmanager(), "eula"); public void oncreateoptionsmenu(menu menu, MenuInflater inflater) { //... inflater.inflate(r.menu.maps_menu, menu); public boolean onoptionsitemselected(menuitem item) { switch (item.getitemid()) { case R.id.menu_showcurrentlocation: Log.d(TAG, "Showing current location"); if (haslocationpermission()) { findlocation(); else { /* Request permissions */ break; return true; 13

Map Fragment Code: Java (5) // MapsFragment.java (continued) public void onrequestpermissionsresult(...) { mlocationpermissiongranted = false; switch (requestcode) { case REQUEST_LOCATION_PERMISSIONS: { // If request is cancelled, the result arrays are empty. if (grantresults.length > 0 && grantresults[0] == PackageManager.PERMISSION_GRANTED) { mlocationpermissiongranted = true; updatelocationui(); private void updatelocationui() { if (mmap == null) { return; try { if (mlocationpermissiongranted) { /* Enable location */ else { /* Disable location, request permissions */ catch (SecurityException e) { /*... */ public void onmapready(googlemap googlemap) { mmap = googlemap; mmap.addmarker(new MarkerOptions().position(new LatLng(40.0, -83.0)).title("Ohio State University")); mmap.setmylocationenabled(true); mmap.getuisettings().setmylocationbuttonenabled(true); /*... */ private boolean haslocationpermission() { /*... */ 14

Map Fragment Code: Kotlin (1) // MapsFragment.kt class MapsFragment : SupportMapFragment(), OnMapReadyCallback { private lateinit var mmap: GoogleMap private lateinit var mapiclient: GoogleApiClient private lateinit var mfusedlocationproviderclient: FusedLocationProviderClient private var mlocation: Location? = null private var mdefaultlocation: LatLng? = null private var mlocationpermissiongranted = false private var mmapready = false companion object { private val LOCATION_PERMISSIONS = arrayof(manifest.permission.access_fine_location, Manifest.permission.ACCESS_COARSE_LOCATION) private val REQUEST_LOCATION_PERMISSIONS = 0 15

Map Fragment Code: Kotlin (2) // MapsFragment.kt (continued) override fun oncreate(savedinstancestate: Bundle?) { super.oncreate(savedinstancestate) sethasoptionsmenu(true) mapiclient = GoogleApiClient.Builder(activity).addApi(LocationServices.API).addConnectionCallbacks(object : GoogleApiClient.ConnectionCallbacks { override fun onconnected(bundle: Bundle?) { activity.invalidateoptionsmenu() override fun onconnectionsuspended(i: Int) {... ).build() getmapasync(this) override fun onresume() { super.onresume() setupeula() findlocation() 16

Map Fragment Code: Kotlin (3) // MapsFragment.kt (continued) override fun onstart() { //... activity.invalidateoptionsmenu() mapiclient.connect() override fun onstop() { //... mapiclient.disconnect() private fun findlocation() { updatelocationui() if (haslocationpermission()) { mfusedlocationproviderclient = LocationServices.getFusedLocationProviderClient(activity) mdefaultlocation = LatLng(40.0, -83.0) val locationrequest = LocationRequest.create() locationrequest.priority = LocationRequest.PRIORITY_HIGH_ACCURACY locationrequest.numupdates = 1 locationrequest.interval = 0 val locationprovider = LocationServices.getFusedLocationProviderClient(activity) val locationresult = locationprovider.lastlocation locationresult.addoncompletelistener(activity, object : OnCompleteListener<Location> { override fun oncomplete(task: Task<Location>) { if (task.issuccessful) { // Set the map's camera position to the current location of the device. mlocation = task.result as Location mmap.movecamera(cameraupdatefactory.newlatlngzoom( LatLng(mLocation!!.latitude, mlocation!!.longitude), 16f)) else { /* Disable location */ ) // Else request permissions, end of method. 17

Map Fragment Code: Kotlin (4) // MapsFragment.kt (continued) private fun setupeula() { msettings = activity.getsharedpreferences(getstring(r.string.prefs), 0) val iseulaaccepted = msettings!!.getboolean(getstring(r.string.eula_accepted_key), false) if (!iseulaaccepted) { val euladialogfragment = EulaDialogFragment() euladialogfragment.show(activity.supportfragmentmanager, "eula") override fun oncreateoptionsmenu(menu: Menu?, inflater: MenuInflater?) { super.oncreateoptionsmenu(menu, inflater) inflater?.inflate(r.menu.maps_menu, menu) override fun onoptionsitemselected(item: MenuItem?): Boolean { when (item?.itemid) { R.id.menu_showcurrentlocation -> { Log.d(TAG, "Showing current location") if (haslocationpermission()) { findlocation() else { requestpermissions(location_permissions, REQUEST_LOCATION_PERMISSIONS) return true 18

Map Fragment Code: Kotlin (5) // MapsFragment.kt (continued) override fun onrequestpermissionsresult(requestcode: Int, permissions: Array<String>, grantresults: IntArray) { mlocationpermissiongranted = false when (requestcode) { REQUEST_LOCATION_PERMISSIONS -> { // If request is cancelled, the result arrays are empty. if (grantresults.isnotempty() && grantresults[0] == PackageManager.PERMISSION_GRANTED) { mlocationpermissiongranted = true updatelocationui() private fun updatelocationui() { if (mmapready) { try { if (mlocationpermissiongranted) { mmap.ismylocationenabled = true mmap.uisettings.ismylocationbuttonenabled = true else { /* Disable location, request permissions */ catch (e: SecurityException) { Log.e("Exception: %s", e.message) /*... */ override fun onmapready(googlemap: GoogleMap) { mmap = googlemap mmap.addmarker(markeroptions().position(latlng(40.0, -83.0)).title("Ohio State University")) try { mmap.ismylocationenabled = true mmap.uisettings.ismylocationbuttonenabled = true catch (se: SecurityException) { Log.e(TAG, "Location not enabled, skipping") mmap.isbuildingsenabled = true mmap.isindoorenabled = true mmapready = true private fun haslocationpermission(): Boolean { /*... */ 19

Map Menu Layout <menu xmlns:app= "http://schemas.android.com/apk/res-auto" xmlns:android= "http://schemas.android.com/apk/res/android"> <item android:id="@+id/menu_showcurrentlocation" android:orderincategory="100" android:title="@string/show_location" android:icon="@android:drawable/ ic_menu_mylocation" app:showasaction="ifroom"/> </menu> 20

License Agreement Fragment: Java Yes, this is required public class EulaDialogFragment extends DialogFragment { public void seteulaaccepted() { SharedPreferences prefs = getactivity().getsharedpreferences( getstring(r.string.prefs), 0); SharedPreferences.Editor editor = prefs.edit(); editor.putboolean(getstring(r.string.eula_accepted_key), true).apply(); public Dialog oncreatedialog(bundle savedinstancestate) { AlertDialog.Builder builder = new AlertDialog.Builder(getActivity()); builder.settitle(r.string.eula_title).setmessage(html.fromhtml(getstring(r.string.eula))).setpositivebutton(r.string.accept, new DialogInterface.OnClickListener() { public void onclick(dialoginterface dialog, int id) { seteulaaccepted(); ).setnegativebutton(r.string.decline, new DialogInterface.OnClickListener() { public void onclick(dialoginterface dialog, int which) { dialog.cancel(); getactivity().finish(); ); return builder.create(); 21

License Agreement Fragment: Kotlin class EulaDialogFragment : DialogFragment() { fun seteulaaccepted() { val prefs = activity.getsharedpreferences(getstring(r.string.prefs), 0) val editor = prefs.edit() editor.putboolean(getstring(r.string.eula_accepted_key), true).apply() override fun oncreatedialog(savedinstancestate: Bundle?): Dialog { // Use the Builder class for convenient dialog construction val builder = AlertDialog.Builder(activity) builder.settitle(r.string.about_app).setmessage(html.fromhtml(getstring(r.string.eula))).setpositivebutton(r.string.accept) { dialog, id -> seteulaaccepted().setnegativebutton(r.string.decline) { dialog, which -> dialog.cancel() activity.finish() return builder.create() 22

Location Determination and Practices Types: GPS Cellular WiFi Best practices for location-based applications: Check for connectivity Use threading to ensure responsiveness (Note: Threading built-in for many SDK components) 23

References Chapter 10: Channeling the Outside World through your Android Device from Android SDK 3 Programming for Dummies Chapters 33 34: Locations and Play Services and Maps from Android Programming: The Big Nerd Ranch Guide (3rd ed.) http://developer.android.com/reference/android/webkit/packagesummary.html http://developer.android.com/reference/android/webkit/webview.html https://developers.google.com/maps/documentation/android/start https://developer.android.com/guide/components/fragments.html https://developer.android.com/training/basics/fragments/creating.html 24

Thank You Questions and comments? 25