Differences

This shows you the differences between two versions of the page.

Link to this comparison view

eim:laboratoare:laborator05 [2016/03/25 07:11]
tmp.andrei.cojocaru
eim:laboratoare:laborator05 [2021/04/04 23:29] (current)
madalina.barbu [Activitate de Laborator]
Line 49: Line 49:
 Αtributul [[http://​developer.android.com/​guide/​topics/​manifest/​service-element.html#​nm|android:​name]] este singurul **obligatoriu** în cadrul elementului ''<​service>'',​ desemnând clasa care gestionează operațiile specifice serviciului respectiv. Din momentul în care aplicația Android este publicată, această valoare nu mai poate fi modificată,​ întrucât poate avea un efect asupra componentelor care utilizează acest serviciu prin intermediul unei intenții explicite folosită la pornirea serviciului sau la asocierea componentei cu serviciul respectiv. Αtributul [[http://​developer.android.com/​guide/​topics/​manifest/​service-element.html#​nm|android:​name]] este singurul **obligatoriu** în cadrul elementului ''<​service>'',​ desemnând clasa care gestionează operațiile specifice serviciului respectiv. Din momentul în care aplicația Android este publicată, această valoare nu mai poate fi modificată,​ întrucât poate avea un efect asupra componentelor care utilizează acest serviciu prin intermediul unei intenții explicite folosită la pornirea serviciului sau la asocierea componentei cu serviciul respectiv.
  
-<note warning>​Pentru a asigura securitatea aplicației Android, se recomandă să se folosească numai **intenții explicite** pentru pornirea unui serviciu. Nu este recomandat să se utilizeze filtre de intenții, astfel încât acestea nu ar trebui să se regăsească în fișierul ''​ΑndroidManifest.xml''​. Totuși, în situația în care acest lucru este absolut necesar, ar trebui să se indice intenției măcar pachetul în care se regăsește serviciul respectiv.</​note>​+<note warning>​Pentru a asigura securitatea aplicației Android, se recomandă să se folosească numai **intenții explicite** pentru pornirea unui serviciu. Nu este recomandat să se utilizeze filtre de intenții, astfel încât acestea nu ar trebui să se regăsească în fișierul ''​ΑndroidManifest.xml''​. Totuși, în situația în care acest lucru este absolut necesar, ar trebui să se indice intenției măcar pachetul în care se regăsește serviciul respectiv. Începând cu Android 5.0, tentativa de pornire a unui serviciu folosind intenții implicite determină excepție, fiind nepermisă.</​note>​
  
 Atributul ''​android:​enabled''​ indică dacă serviciul poate fi instanțiat de către sistemul de operare. Atributul ''​android:​enabled''​ indică dacă serviciul poate fi instanțiat de către sistemul de operare.
Line 314: Line 314:
  
 === Servicii de tip Bounded === === Servicii de tip Bounded ===
 +<spoiler (Opțional)> ​
 Un serviciu de tip bounded implică o interacțiune permanentă cu una sau mai multe componente ale unei (unor) aplicații Android. Astfel, serviciul poate expune o anumită funcționalitate către componentele aplicației Android (prin intermediul unei interfețe) sau poate fi utilizat ca mecanism de comunicație inter-proces,​ pentru transmiterea de informații între acestea. Un serviciu de tip bounded implică o interacțiune permanentă cu una sau mai multe componente ale unei (unor) aplicații Android. Astfel, serviciul poate expune o anumită funcționalitate către componentele aplicației Android (prin intermediul unei interfețe) sau poate fi utilizat ca mecanism de comunicație inter-proces,​ pentru transmiterea de informații între acestea.
  
Line 451: Line 451:
  
 Dacă este necesar ca procesarea să fie realizată simultan, poate fi utilizat AIDL (Android Interface Definition Language) care realizează transformarea dintre obiecte și primitive la nivelul sistemului de operare prin intermediul cărora se realizează comunicația inter-proces. În această situație, trebuie avut în vedere faptul că sincronizarea dintre diferitele fire de execuție trebuie realizată manual, operație destul de complexă. Pe baza fișierului ''​.aidl''​ care descrie interfața de programare, se va genera o clasă abstractă responsabilă cu comunicația inter-proces,​ din care va fi derivat serviciul respectiv. Dacă este necesar ca procesarea să fie realizată simultan, poate fi utilizat AIDL (Android Interface Definition Language) care realizează transformarea dintre obiecte și primitive la nivelul sistemului de operare prin intermediul cărora se realizează comunicația inter-proces. În această situație, trebuie avut în vedere faptul că sincronizarea dintre diferitele fire de execuție trebuie realizată manual, operație destul de complexă. Pe baza fișierului ''​.aidl''​ care descrie interfața de programare, se va genera o clasă abstractă responsabilă cu comunicația inter-proces,​ din care va fi derivat serviciul respectiv.
 +</​spoiler> ​
 ==== Prioritatea unui Serviciu ==== ==== Prioritatea unui Serviciu ====
  
Line 477: Line 477:
  
 <code java> <code java>
-Notification notification ​= new Notification(R.drawable.icon,  +NotificationCompat.Builder notificationBuilder ​= 
-                                             ​"​..."​, +    ​new NotificationCompat.Builder(this) 
-                                             System.currentTimeMillis());+    .setSmallIcon(R.drawable.notification_icon) 
 +    ​.setContentTitle("​..."​) 
 +    .setContentText("​..."​);
 Intent intent = new Intent(this,​ SomeActivity.class);​ Intent intent = new Intent(this,​ SomeActivity.class);​
-PendingIntent pendingIntent = PendingIntent.getActivity(this,​ 0, intent, ​0); +PendingIntent pendingIntent = PendingIntent.getActivity(this,​ 0, intent, ​PendingIntent.FLAG_UPDATE_CURRENT); 
-notification.setLatestEventInfo(this,  +notificationBuilder.setContentIntent(pendingIntent);​ 
-                                "​...", +Notification notification = notificationBuilder.build();
-                                "​...",​  +
-                                pendingIntent);+
 startForeground(NOTIFICATION_ID,​ notification);​ startForeground(NOTIFICATION_ID,​ notification);​
 </​code>​ </​code>​
Line 633: Line 633:
  
 ==== Realizarea de Procesări prin Intermediul Alarmelor ==== ==== Realizarea de Procesări prin Intermediul Alarmelor ====
 +<spoiler (Opțional)> ​
  
 O alarmă reprezintă un mecanism de transmitere a unor intenții la momente predefinite de timp sau periodic, după trecerea unui anumit interval. Acestea există în afara domeniului de existență a unei aplicații Android, astfel încât acestea pot fi utilizate pentru a realiza anumite acțiuni chiar și în situația în care acestea nu mai există. Din acest motiv, alarmele reprezintă o metodă foarte utilă pentru a difuza intenții, pentru a porni servicii sau lansa în execuție activități,​ fără a fi necesar ca aplicația să se afle în execuție. Se asigură astfel și optimizarea cerințelor legate de resursele utilizate de aplicație. O alarmă reprezintă un mecanism de transmitere a unor intenții la momente predefinite de timp sau periodic, după trecerea unui anumit interval. Acestea există în afara domeniului de existență a unei aplicații Android, astfel încât acestea pot fi utilizate pentru a realiza anumite acțiuni chiar și în situația în care acestea nu mai există. Din acest motiv, alarmele reprezintă o metodă foarte utilă pentru a difuza intenții, pentru a porni servicii sau lansa în execuție activități,​ fără a fi necesar ca aplicația să se afle în execuție. Se asigură astfel și optimizarea cerințelor legate de resursele utilizate de aplicație.
Line 685: Line 686:
  
 Anularea unei alarme recurente se face tot prin intermediul metodei [[http://​developer.android.com/​reference/​android/​app/​AlarmManager.html#​cancel(android.app.PendingIntent)|cancel()]] a obiectului de tip ''​AlarmManager''​ care primește ca parametru intenția în așteptare care nu mai trebuie transmisă. Anularea unei alarme recurente se face tot prin intermediul metodei [[http://​developer.android.com/​reference/​android/​app/​AlarmManager.html#​cancel(android.app.PendingIntent)|cancel()]] a obiectului de tip ''​AlarmManager''​ care primește ca parametru intenția în așteptare care nu mai trebuie transmisă.
 +</​spoiler>​
 +
 +===== Utilitare =====
 +  * Listare servicii din acest laborator <​code>​ adb shell dumpsys activity services | grep lab05 </​code>,​ doar cele pornite sunt afișate
 +  * Listare pachete <​code>​ adb shell pm list packages -f | grep lab05</​code>​
 +  * Oprire forțată a unui serviciu <​code>​am force-stop ro.pub.cs.systems.eim.lab05.startedservice</​code>​
 +  * Pornire <​code>​am startservice ro.pub.cs.systems.eim.lab05.startedservice/​.service.StartedService </​code>​
 +  * Pornire în oreo <​code>​am start-foreground-service ro.pub.cs.systems.eim.lab05.startedservice/​.service.StartedService </​code>​
 +  * Utilitarul MyAndroidTools (preinstalat în genymotion) listează activitățile și serviciile unei aplicații. Pentru servicii sunt două coloane: servicii pornite (albastru) si servicii disponibile(negru).  ​
 +  * În Android Studio/​Tool/​Android/​Android Device Monitor - se deschide perspectiva DDMS care oferă control asupra proceselor și thread-urilor care rulează în emulator/​telefon. ​
  
 ===== Activitate de Laborator ===== ===== Activitate de Laborator =====
Line 690: Line 701:
 **1.** În contul Github personal, să se creeze un depozit denumit '​Laborator05'​. Inițial, acesta trebuie să fie gol (nu trebuie să bifați nici adăugarea unui fișier README.md, nici a fișierului .gitignore sau a a fișierului LICENSE). **1.** În contul Github personal, să se creeze un depozit denumit '​Laborator05'​. Inițial, acesta trebuie să fie gol (nu trebuie să bifați nici adăugarea unui fișier README.md, nici a fișierului .gitignore sau a a fișierului LICENSE).
  
-**2.** Să se cloneze în directorul de pe discul local conținutul depozitului la distanță de la https://​www.github.com/​eim2016/​Laborator05. În urma acestei operații, directorul Laborator05 va trebui să se conțină un director ''​labtasks''​ ce va deține proiectele AndroidStudio ​respectiv Eclipse, fișierul README.md și un fișier .gitignore care indică tipurile de fișiere (extensiile) ignorate.+**2.** Să se cloneze în directorul de pe discul local conținutul depozitului la distanță de la https://​www.github.com/​eim-lab/​Laborator05. În urma acestei operații, directorul Laborator05 va trebui să se conțină un director ''​labtasks''​ ce va deține proiectele AndroidStudio,​ fișierul README.md și un fișier .gitignore care indică tipurile de fișiere (extensiile) ignorate.
  
 <​code>​ <​code>​
-student@eim2016:~$ git clone https://​www.github.com/​eim2016/​Laborator05.git+student@eim:~$ git clone https://​www.github.com/​eim-lab/​Laborator05.git
 </​code>​ </​code>​
  
Line 699: Line 710:
  
 <​code>​ <​code>​
-student@eim2016:~$ cd Laborator05 +student@eim:~$ cd Laborator05 
-student@eim2016:​~/​Laborator05$ git remote add Laborator05_perfectstudent https://​github.com/​perfectstudent/​Laborator05 +student@eim:​~/​Laborator05$ git remote add Laborator05_perfectstudent https://​github.com/​perfectstudent/​Laborator05 
-student@eim2016:​~/​Laborator05$ git push Laborator05_perfectstudent master+student@eim:​~/​Laborator05$ git push Laborator05_perfectstudent master
 </​code>​ </​code>​
  
-**4.** Să se încarce în mediul integrat de dezvoltare ​preferat (Android Studio ​sau Eclipse) ​proiectele //​StartedService//​ respectiv //​StartedServiceActivity//​ din directorul ''​labtasks/<​IDE>​/​StartedService''​.+**4.** Să se încarce în mediul integrat de dezvoltare Android Studio proiectele //​StartedService//​ respectiv //​StartedServiceActivity//​ din directorul ''​labtasks/​StartedService''​.
  
   * Proiectul //​StartedService//​ conține codul sursă pentru un serviciu de tip started care transmite mai multe valori, de diferite tipuri (șir de caractere, întreg, vector), temporizate la un anumit interval (dată de valoarea ''​SLEEP_TIME''​ din interfața ''​Constants''​). Aceste valori sunt transmise prin intermediul unor intenții cu difuzare (//eng.// broadcast intents), la nivelul întregului sistem de operare Android.   * Proiectul //​StartedService//​ conține codul sursă pentru un serviciu de tip started care transmite mai multe valori, de diferite tipuri (șir de caractere, întreg, vector), temporizate la un anumit interval (dată de valoarea ''​SLEEP_TIME''​ din interfața ''​Constants''​). Aceste valori sunt transmise prin intermediul unor intenții cu difuzare (//eng.// broadcast intents), la nivelul întregului sistem de operare Android.
   * Proiectul //​StartedServiceActivity//​ conține codul sursă pentru o aplicație Android care utilizează un ascultător pentru intenții cu difuzare (//eng.// BroadcastReceiver),​ pentru tipurile de mesaje propagate la nivelul sistemului de operare de către serviciu, pe care le afișează în interfața grafică, prin intermediul unui câmp text.   * Proiectul //​StartedServiceActivity//​ conține codul sursă pentru o aplicație Android care utilizează un ascultător pentru intenții cu difuzare (//eng.// BroadcastReceiver),​ pentru tipurile de mesaje propagate la nivelul sistemului de operare de către serviciu, pe care le afișează în interfața grafică, prin intermediul unui câmp text.
  
-{{ :​eim:​laboratoare:​laborator05:​activitate_de_laborator01.png?​nolink&​400 }}+{{ :​eim:​laboratoare:​laborator05:​startedservice.png?​nolink&​400 }}
  
 **5.** În proiectul //​StartedService//,​ în clasa ''​StartedService''​ din pachetul ''​ro.pub.cs.systems.eim.lab05.startedservice.service'',​ să se completeze metoda ''​onStartCommand()''​ astfel încât aceasta să pornească un fir de execuție în cadrul căruia să fie propagate 3 intenții cu difuzare la nivelul sistemului de operare Android. ​ **5.** În proiectul //​StartedService//,​ în clasa ''​StartedService''​ din pachetul ''​ro.pub.cs.systems.eim.lab05.startedservice.service'',​ să se completeze metoda ''​onStartCommand()''​ astfel încât aceasta să pornească un fir de execuție în cadrul căruia să fie propagate 3 intenții cu difuzare la nivelul sistemului de operare Android. ​
Line 778: Line 789:
  
 Monitorizați ciclurile din Thread.run() in logcat: Monitorizați ciclurile din Thread.run() in logcat:
-<​code>​ +<​code ​java
-Log.d(Constants.TAG,​ "​Thread.run() was invoked, PID:" + android.os.Process.myPid() + " TID:" + android.os.Process.myTid());​+Log.d(Constants.TAG,​ "​Thread.run() was invoked, PID: " + android.os.Process.myPid() + " TID: " + android.os.Process.myTid());​
 </​code>​ </​code>​
- 
  
 **6.** În proiectul //​StartedServiceActivity//,​ să se pornească serviciul, printr-un apel al metodei [[http://​developer.android.com/​reference/​android/​content/​Context.html#​startService%28android.content.Intent%29|startService()]];​ intenția care va fi transmisă ca argument metodei ''​startService()''​ trebuie să refere **explicit** serviciul care urmează a fi pornit, din motive de securitate (se folosește metoda [[http://​developer.android.com/​reference/​android/​content/​Intent.html#​setComponent%28android.content.ComponentName%29|setComponent()]],​ care indică atât pachetul corespunzător aplicației Android care conține serviciul, cât și clasa corespunzătoare acestuia - calificată complet). **6.** În proiectul //​StartedServiceActivity//,​ să se pornească serviciul, printr-un apel al metodei [[http://​developer.android.com/​reference/​android/​content/​Context.html#​startService%28android.content.Intent%29|startService()]];​ intenția care va fi transmisă ca argument metodei ''​startService()''​ trebuie să refere **explicit** serviciul care urmează a fi pornit, din motive de securitate (se folosește metoda [[http://​developer.android.com/​reference/​android/​content/​Intent.html#​setComponent%28android.content.ComponentName%29|setComponent()]],​ care indică atât pachetul corespunzător aplicației Android care conține serviciul, cât și clasa corespunzătoare acestuia - calificată complet).
Line 795: Line 805:
 **a)** Să se ruleze aplicațiile. Se va rula aplicația //​StartedService//​ care instalează serviciul pe dispozitivul mobil. Ulterior se va rula aplicația //​StartedServiceActivity//​. Verificați faptul că serviciul a fost pornit și oprit corespunzător prin mesajele afișate în consolă. **a)** Să se ruleze aplicațiile. Se va rula aplicația //​StartedService//​ care instalează serviciul pe dispozitivul mobil. Ulterior se va rula aplicația //​StartedServiceActivity//​. Verificați faptul că serviciul a fost pornit și oprit corespunzător prin mesajele afișate în consolă.
  
-**b)** Monitorizați în DDMS procesele asociate activității și serviciului. Ce se întâmplă dacă activitatea este eliminată (onDestroy)?​+**b)** Monitorizați în DDMS procesele asociate activității și serviciului. Ce se întâmplă dacă activitatea este eliminată (''​onDestroy()''​)?
  
-**c)**Explicați ce se întâmplă dacă restartăm ​activitatea(Monitorizați în DDMS si logcat). ​+**c)** Explicați ce se întâmplă dacă repornim ​activitatea (monitorizați în DDMS si logcat). ​
  
 **7.** În proiectul //​StartedServiceActivity//,​ să se implementeze un ascultător pentru intenții cu difuzare, în clasa ''​StartedServiceBroadcastReceiver''​ din pachetul ''​ro.pub.cs.systems.eim.lab05.startedserviceactivity.view''​. Acesta extinde clasa [[http://​developer.android.com/​reference/​android/​content/​BroadcastReceiver.html|BroadcastReceiver]] și implementează metoda [[http://​developer.android.com/​reference/​android/​content/​BroadcastReceiver.html#​onReceive%28android.content.Context,​%20android.content.Intent%29|onReceive()]],​ având ca argumente **contextul** din care a fost invocată și **intenția** prin intermediul căreia a fost transmis mesajul respectiv. Astfel, datele extrase din intenție (având cheia indicată de ''​Constants.DATA''​) vor fi afișate într-un câmp text (''​messageTextView''​) din cadrul interfeței grafice. **7.** În proiectul //​StartedServiceActivity//,​ să se implementeze un ascultător pentru intenții cu difuzare, în clasa ''​StartedServiceBroadcastReceiver''​ din pachetul ''​ro.pub.cs.systems.eim.lab05.startedserviceactivity.view''​. Acesta extinde clasa [[http://​developer.android.com/​reference/​android/​content/​BroadcastReceiver.html|BroadcastReceiver]] și implementează metoda [[http://​developer.android.com/​reference/​android/​content/​BroadcastReceiver.html#​onReceive%28android.content.Context,​%20android.content.Intent%29|onReceive()]],​ având ca argumente **contextul** din care a fost invocată și **intenția** prin intermediul căreia a fost transmis mesajul respectiv. Astfel, datele extrase din intenție (având cheia indicată de ''​Constants.DATA''​) vor fi afișate într-un câmp text (''​messageTextView''​) din cadrul interfeței grafice.
Line 881: Line 891:
 </​spoiler>​ </​spoiler>​
  
-**d)** ​ +**d)** Să se oprească serviciul printr-un apel al metodei [[http://​developer.android.com/​reference/​android/​content/​Context.html#​stopService%28android.content.Intent%29|stopService()]]. Unde ar putea fi plasată aceasta? Care sunt avantajele și dezavantajele unei astfel de abordări?
-Să se oprească serviciul printr-un apel al metodei [[http://​developer.android.com/​reference/​android/​content/​Context.html#​stopService%28android.content.Intent%29|stopService()]]. Unde ar putea fi plasată aceasta? Care sunt avantajele și dezavantajele unei astfel de abordări?+
  
 **9.** Rulați din nou aplicația, întrerupând temporar activitatea (printr-o apăsare a tastei //Home//) în timp ce sunt procesate intențiile cu difuzare transmise de serviciu. Ce observați la revenirea în activitate? **9.** Rulați din nou aplicația, întrerupând temporar activitatea (printr-o apăsare a tastei //Home//) în timp ce sunt procesate intențiile cu difuzare transmise de serviciu. Ce observați la revenirea în activitate?
Line 923: Line 932:
 } }
 </​code>​ </​code>​
 +
 +De remarcat faptul că activitatea poate fi pornită din contextul ascultătorului pentru mesaje cu difuzare, folosind următorii parametri:
 +  * [[https://​developer.android.com/​reference/​android/​content/​Intent.html#​FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_NEW_TASK]] - prin care activitatea este plasată într-un nou set de sarcini pe stivă, pe care utilizatorul le poate gestiona independent;​
 +  * [[https://​developer.android.com/​reference/​android/​content/​Intent.html#​FLAG_ACTIVITY_SINGLE_TOP|Intent.FLAG_ACTIVITY_SINGLE_TOP]] - prin care activitatea nu este repornită dacă se găsește deja la baza stivei care reține istoricul operațiunilor realizate de utilizator.
  
 Astfel, activitatea va fi invocată prin intermediul intenției, în condițiile în care aceasta este activă (se găsește în memorie, fiind plasată pe stiva de activități,​ fără a fi vizibilă). De aceea, aceasta va invoca metoda de callback [[http://​developer.android.com/​reference/​android/​app/​Activity.html#​onNewIntent%28android.content.Intent%29|onNewIntent()]] pe care trebuie realizată afișarea informațiilor transmise în câmpul ''​extra''​ al intenției. Astfel, activitatea va fi invocată prin intermediul intenției, în condițiile în care aceasta este activă (se găsește în memorie, fiind plasată pe stiva de activități,​ fără a fi vizibilă). De aceea, aceasta va invoca metoda de callback [[http://​developer.android.com/​reference/​android/​app/​Activity.html#​onNewIntent%28android.content.Intent%29|onNewIntent()]] pe care trebuie realizată afișarea informațiilor transmise în câmpul ''​extra''​ al intenției.
Line 939: Line 952:
 </​spoiler>​ </​spoiler>​
  
-**10.** Să se încarce în mediul integrat de dezvoltare ​preferat (Android Studio ​sau Eclipse) ​proiectul //​BoundedServiceActivity//​ din directorul ''​labtasks/<​IDE>​/​BoundedService''​. Se dorește să se implementeze un serviciu de tip bounded care poate interacționa cu o activitate prin intermediul unei metode care furnizează un șir de caractere ales aleator dintr-o listă de valori.+**10.** **[Opțional]** Să se încarce în mediul integrat de dezvoltare Android Studio proiectul //​BoundedServiceActivity//​ din directorul ''​labtasks/​BoundedService''​. Se dorește să se implementeze un serviciu de tip bounded care poate interacționa cu o activitate prin intermediul unei metode care furnizează un șir de caractere ales aleator dintr-o listă de valori.
  
 **a)** În clasa ''​BoundedService''​ din pachetul ''​ro.pub.cs.systems.eim.lab05.boundedserviceactivity.service'',​ să se implementeze o clasă internă **publică**,​ derivată din interfața [[http://​developer.android.com/​reference/​android/​os/​IBinder.html|IBinder]],​ care oferă o referință către serviciu prin intermediul metodei **publice** ''​getService()''​. Instanța acestei clase interne va fi furnizată ca rezultat al metodei [[http://​developer.android.com/​reference/​android/​app/​Service.html#​onBind%28android.content.Intent%29|onBind()]]. **a)** În clasa ''​BoundedService''​ din pachetul ''​ro.pub.cs.systems.eim.lab05.boundedserviceactivity.service'',​ să se implementeze o clasă internă **publică**,​ derivată din interfața [[http://​developer.android.com/​reference/​android/​os/​IBinder.html|IBinder]],​ care oferă o referință către serviciu prin intermediul metodei **publice** ''​getService()''​. Instanța acestei clase interne va fi furnizată ca rezultat al metodei [[http://​developer.android.com/​reference/​android/​app/​Service.html#​onBind%28android.content.Intent%29|onBind()]].
Line 1016: Line 1029:
 **e)** Să se implementeze o clasă ascultător pentru evenimentul de tip apăsare corespunzător controlului grafic de tip buton. În cadrul metodei de tratare a evenimentului,​ să se apeleze metoda din cadrul serviciului care furnizează un mesaj aleator și să se afișeze acest mesaj în cadrul câmpului text, împreună cu data și ora la care a fost furnizat. **e)** Să se implementeze o clasă ascultător pentru evenimentul de tip apăsare corespunzător controlului grafic de tip buton. În cadrul metodei de tratare a evenimentului,​ să se apeleze metoda din cadrul serviciului care furnizează un mesaj aleator și să se afișeze acest mesaj în cadrul câmpului text, împreună cu data și ora la care a fost furnizat.
  
-{{ :​eim:​laboratoare:​laborator05:​activitate_de_laborator02.png?​nolink&​400 }}+{{ :​eim:​laboratoare:​laborator05:​boundedservice.png?​nolink&​400 }}
  
 <spoiler Indicații de Rezolvare>​ <spoiler Indicații de Rezolvare>​
Line 1036: Line 1049:
  
 <​code>​ <​code>​
-student@eim2016:​~/​Laborator05$ git add labtasks/​* +student@eim:​~/​Laborator05$ git add labtasks/​* 
-student@eim2016:​~/​Laborator05$ git commit -m "​implemented taks for laboratory 05" +student@eim:​~/​Laborator05$ git commit -m "​implemented taks for laboratory 05" 
-student@eim2016:​~/​Laborator05$ git push Laborator05_perfectstudent master+student@eim:​~/​Laborator05$ git push Laborator05_perfectstudent master
 </​code>​ </​code>​
 ===== Resurse Utile ===== ===== Resurse Utile =====
Line 1051: Line 1064:
 [[http://​ptgmedia.pearsoncmg.com/​images/​9780321940261/​samplepages/​0321940261.pdf|Joseph ANNUZZI, Jr, Lauren DARCEY, Shane CONDER, Introduction to Android Application Development - Developer'​s Library, 4th Edition, Addison-Wesley,​ 2013]] - capitolul 4, subcapitolele //Working with Services//, //Receiving and Broadcasting Intents//​\\ ​ [[http://​ptgmedia.pearsoncmg.com/​images/​9780321940261/​samplepages/​0321940261.pdf|Joseph ANNUZZI, Jr, Lauren DARCEY, Shane CONDER, Introduction to Android Application Development - Developer'​s Library, 4th Edition, Addison-Wesley,​ 2013]] - capitolul 4, subcapitolele //Working with Services//, //Receiving and Broadcasting Intents//​\\ ​
 [[http://​www.bignerdranch.com/​we-write/​android-programming/​|Bill PHILLIPS, Brian HARDY, Android Programming. The Big Nerd Ranch Guide, Pearson Technology Group, 2013]] - capitolele 29 (//​Background Services//​),​ 30 (//​Broadcast Intents//​)\\ ​ [[http://​www.bignerdranch.com/​we-write/​android-programming/​|Bill PHILLIPS, Brian HARDY, Android Programming. The Big Nerd Ranch Guide, Pearson Technology Group, 2013]] - capitolele 29 (//​Background Services//​),​ 30 (//​Broadcast Intents//​)\\ ​
 +
 +===== Android Developer Fundamentals =====
 +[[https://​docs.google.com/​presentation/​d/​1SdawmBYLrDKcLxwtvB09B5ffK7Bd9cj-677qI5Unekg/​edit#​slide=id.g116d7d9d49_3_13 | Services]]\\
 +[[https://​docs.google.com/​presentation/​d/​1A7anDTS8NQCunbxoJnqJqkSHNFCvRIn9moE7Zww-gds/​edit#​slide=id.g116d7d9d49_3_13 | AsyncTask]]\\
 +[[https://​docs.google.com/​presentation/​d/​1qF9Yeau7uHIP7_aOHWgPU_RnfxACZzGyAZIzcJWz0R0/​edit#​slide=id.g116d7d9d49_3_13 | Broadcasts]]
eim/laboratoare/laborator05.1458882695.txt.gz · Last modified: 2016/03/25 07:11 by tmp.andrei.cojocaru
CC Attribution-Share Alike 3.0 Unported
www.chimeric.de Valid CSS Driven by DokuWiki do yourself a favour and use a real browser - get firefox!! Recent changes RSS feed Valid XHTML 1.0