Tvorba aplikací pro mobilní zařízení

Slides:



Advertisements
Podobné prezentace
© 2000 VEMA počítače a projektování spol. s r. o..
Advertisements

Stodůlky 1977 a 2007 foto Václav Vančura, 1977 foto Jan Vančura, 2007.
Vlastní skript může být umístěn: v hlavičce stránky v těle stránky
VÝVOJ PROGRAMOVACÍCH JAZYKŮ PERSPEKTIVY ELEKTRONIKY 3. Celostátní seminář, 18. března 2003 Ing. Pavel Pokorný UNIVERZITA TOMÁŠE BATI VE ZLÍNĚ Fakulta technologická.
Pascal - příklady.
CSS a HTML 5. HTML 5 HTML5 je nová verze specifikace značkovacího jazyka HTML, která přináší podstatné změny v technologiích webových stránek. HTML5 umožňuje.
Aktuální informace o vyšetřování c-erb-2 genu v referenční laboratoři a návrh změny v indikačních kritériích Hajdúch M., Petráková K., Kolář Z., Trojanec.
MS Malování II. VY_32_INOVACE_58_MS_Malovani_II.
Počítače a programování 1. Obsah přednášky Výjimky - základní typy výjimek Způsoby zpracování výjimek.
C# pro začátečníky Mgr. Jaromír Osčádal
Téma 3 ODM, analýza prutové soustavy, řešení nosníků
PHP – vkládání souborů a html 5
Operační systém Adam Greguš, 4.A.
Výzkumy volebních preferencí za ČR a kraje od
NÁSOBENÍ ČÍSLEM 10 ZÁVĚREČNÉ SHRNUTÍ
Téma: SČÍTÁNÍ A ODČÍTÁNÍ CELÝCH ČÍSEL 2
VY_32_INOVACE_INF_RO_12 Digitální učební materiál
SmartPhone start - Apple iPhone
VY_32_INOVACE_ 14_ sčítání a odčítání do 100 (SADA ČÍSLO 5)
Definování prostředí pro provozování aplikace dosud jsme řešili projekt v obecné rovině aplikace bude ovšem provozována v konkrétním technickém a programovém.
Zábavná matematika.
Dělení se zbytkem 6 MODERNÍ A KONKURENCESCHOPNÁ ŠKOLA
Letokruhy Projekt žáků Střední lesnické školy a střední odborné školy sociální ve Šluknově.
State. State – kontext a problém Kontext  chování objektu má záviset na jeho stavu, který se typicky mění za běhu Neflexibilní řešení  metody obsahují.
Jazyk vývojových diagramů
Čtení myšlenek Je to až neuvěřitelné, ale skutečně je to tak. Dokážu číst myšlenky.Pokud mne chceš vyzkoušet – prosím.
Únorové počítání.
OS Windows. Tento operační systém byl vytvořen pro snazší ovládání počítače běžnými uživateli. Například stačí jednou definovat připojená zařízení (tiskárny…)
Dělení se zbytkem 8 MODERNÍ A KONKURENCESCHOPNÁ ŠKOLA
Náhoda, generátory náhodných čísel
Zásady pozorování a vyjednávání Soustředění – zaznamenat (podívat se) – udržet (zobrazit) v povědomí – představit si – (opakovat, pokud se nezdaří /doma/)
SČÍTÁNÍ A ODČÍTÁNÍ V OBORU DO 100
Hrubá - prostá incidence nádorů kolorekta u mužů 1. Maďarsko 88,29 2. Česká Republika 86,73 3. Japonsko 77,74 4. Německo 75,39 5. Nový Zéland71,77 6. Austrálie.
Maturitní okruh č. 7. Odstínit aplikace od specifik HWSpráva procesůSpráva pamětiSpráva souborůSpráva vstupů a výstupůSpráva sítěSystém ochrany a bezpečnostiSystém.
DĚLENÍ ČÍSLEM 7 HLAVOLAM DOPLŇOVAČKA PROCVIČOVÁNÍ
Orbis pictus 21. století Tato prezentace byla vytvořena v rámci projektu.
Operační systémy.
J2ME Martin Orlich Titulní stránka. JAVA Programovací jazyk Java je poskytován firmou Sun Microsystems ve třech vydáních: Java 2 Standard Edition Java.
Orbis pictus 21. století Tato prezentace byla vytvořena v rámci projektu.
Operační systém (OS) ICT Informační a komunikační technologie.
Gymnázium, SOŠ a VOŠ Ledeč nad Sázavou I NFORMAČNÍ A KOMUNIKAČNÍ TECHNOLOGIE Ing. Jan Roubíček.
2 Ing. Jan Keprt Centrální správa uživatelů 3 Jak to bylo dosud Bylo třeba nastavení uživatelů provést zvlášť, v každém modulu samostatně. Uživatel si.
KONTROLNÍ PRÁCE.
Návrh a tvorba WWW Přednáška 5 Úvod do jazyka PHP.
Porovnání výroby a prodejů vozidel ve světě
Gymnázium, SOŠ a VOŠ Ledeč nad Sázavou I NFORMAČNÍ A KOMUNIKAČNÍ TECHNOLOGIE Ing. Jan Roubíček.
Dědičnost - inheritance dědičnost je jednou z forem znovupoužitelnosti dědičnost je jednou z forem znovupoužitelnosti B A Třída A je předkem třídy B Třída.
PROJEKT : SCADA systémy na mobilních zařízeních AUTOŘI : Ing. Ondřej Krejcar Ing. Stanislav Slíva.
7. Typ soubor Souborem dat běžně rozumíme uspořádanou množinu dat, uloženou mimo operační paměť počítače (na disku). Pascalský soubor je abstrakcí skutečného.
Martina Braunerová.  nejdůležitější program v počítači  umožňuje všem ostatním programům fungovat  prostředník mezi počítačem a uživatelem.
Šesté cvičení Výjimky Balíky.
Orbis pictus 21. století Tato prezentace byla vytvořena v rámci projektu.
ZÁPADOČESKÁ UNIVERZITA V PLZNI FAKULTA ELEKTROTECHNICKÁ KATEDRA TEORETICKÉ ELEKTROTECHKY Oddělení informatiky Java Micro Edition pro mobilní zařízení.
OPERAČNÍ SYSTÉMY.
Jazyk C A0B36PRI - PROGRAMOVÁNÍ Část II.
WINDOWS Základní popis a údržba operačních systémů.
Uvedení autoři, není-li uvedeno jinak, jsou autory tohoto výukového materiálu a všech jeho částí. Tento projekt je spolufinancován ESF a státním rozpočtem.
Tento projekt je financován z Operačního programu Vzdělávání pro konkurenceschopnost prostřednictvím Evropského sociálního fondu a státního rozpočtu ČR.
SOFTWAROVÁ PODPORA PRO VYTVÁŘENÍ FUZZY MODELŮ Knihovna fuzzy procedur Ing. Petr Želasko, VŠB-TU Ostrava.
SOFTWARE Operační systémy.
Vypracoval / Roman Málek
OPERAČNÍ SYSTÉMY Číslo projektu CZ.1.07/1.5.00/ Název školy
Vlastnosti souborů Jaroslava Černá.
Operační systémy - úvod
Soubor Soubor v informatice označuje pojmenovanou sadu dat uloženou na nějakém datovém médiu, se kterou lze pracovat nástroji operačního systému jako.
Výukový materiál zpracován v rámci projektu
Návrhový vzor Flyweight
Bridge.
1. ročník oboru Mechanik opravář motorových vozidel
C# přehled vlastností.
Transkript prezentace:

Tvorba aplikací pro mobilní zařízení Rudolf Pecinovský Amaio Technologies

Rozvrh dne Úvod 9:00 – 9:30 Mobilní zařízení a jejich vlastnosti 9:00 – 9:30 Mobilní zařízení a jejich vlastnosti 9:30 – 9:45 Java 2 Micro Edition, konfigurace, profily 9:45 – 10:30 Přestávka 10:30 – 10:45 MIDP, vývojová prostředí, první MIDlet 10:45 – 11:30 Low-level GUI 11:30 – 12:15 Oběd 12:30 – 13:30 Ukázka aplikací 13:30 – 14:00 High-level GUI 14:00 – 14:45 Uchování informací mezi spuštěními 14:45 – 15:30 15:30 – 15:45 Komunikace po síti 15:45 – 16:30 Závěr 16:30 – 17:00

Co od účastníků semináře očekáváme Znalosti základů programování v jazyce Java Chuť dozvědět se něco nového Co se dnes naučíte Možnosti mobilních zařízení, zejména telefonů Základní charakteristiky Java ME Navrhovat aplikace pro Java ME

Co nás čeká Svět mobilních zařízení, Java ME, CLDC, MIDP Mobilní zařízení a jejich vlastnosti Java Micro Edition – Java ME Konfigurace Profily Tvorba aplikací pro MIDP MIDlety a jejich suity Nízkoúrovňové uživatelské rozhraní Práce s grafikou Formulářové uživatelské rozhraní Vnitřní databáze Spolupráce po síti

Mobilní zařízení a jejich vlastnosti

Mobilní aplikace v současném světě Počítače se prosazují v nových oblastech – mimo jiné v mobilních zařízeních Mobilních uživatelů internetu začíná být více než těcht „pevných“ Firmy chtějí umožnit pracovníkům připojení odkudkoliv Klasický počítač – nevhodný Notebook – pro řadu uživatelů stále ještě těžkopádný PDA – vhodný, ale často zbytečně drahý Mobilní telefon – horký kandidát

Mobilní telefon – výhodné vlastnosti Většina lidí jej má u sebe Moderní telefony jsou programovatelné (lze pro ně vyvíjet programy a ty pak do nich nahrát) Obsahují jednoduchý operační systém Umí spouštět připravené aplikace Aplikaci můžete v případě potřeby nejprve nahrát „po telefonu“ Jsou z principu připojitelné do sítě Mohou sloužit jako „tenký klient“

Mobilní telefon – nevýhody Menší operační paměť Bateriové napájení => Pomalejší procesor Malá obrazovka Těžkopádná klávesnice Většinou absence ukazovacího zařízení (myši) Relativně pomalé připojení k síti Absence velké paměti typu HD Výrobci se předhánějí ve vylepšeních Javy, takže vznikají problémy s kompatibilitou

Další programovatelná zařízení v síti PDA (Personal Digital Assistant) Osobní databanky (Personal Organizers) Oboucestné pagery (two-way pagers) Automobilové počítače GPS systémy (Global Position System) Přídavná zařízení (set-top box) Internetové televize Čtečky čárových kódů Zařízení zabudovaná ve spotřební elektronice

Společné vlastnosti Velká variabilita Malá operační paměť Absence velkokapacitní paměti Většinou méně výkonný procesor Nestandardní ovládání, svérázný UI Připojení k síti … ale většinou pomalé Většinou omezené na firmware výrobce Označována jako Pervasive devices (všudypřítomná zařízení)

Shrnutí Mobilní zařízení – výhodná platforma pro umístění řady důležitých aplikací Malý výkon, malá paměť Obrovská rozmanitost všech charakteristik Častá schopnost připojení do sítě

Java Micro Edition Java ME™ První seznámení

Historie Červen 1999 – JavaOneSM Developer Conference Ohlášeny 3 platformy J2ME – Java 2 Micro Edition J2SE – Java 2 Standard Edition J2EE – Java 2 Enterprise Edition Vyvíjena pod JCP – Java Community ProcessSM Červen 2000 – 500 firem se přihlásilo k podpoře Červen 2001 – Prodáno >3 mil. zařízení s J2ME Léto 2002 – objevilo se okolo 50 modelů mobilních telefonů podporujících J2ME

Současnost a budoucnost V průběhu 5 let by měla být využívána asi 1 miliarda telefonů podporujících J2ME Počáteční boom zabily výrobci telefonů, protože každý implementoval specifikaci trochu jinak, takže vznikaly problémy s kompatibilitou Java ME je stále jedinou platformou dostupnou prakticky na všech mobilních zařízeních včetně těch nejlevnějších Android a Apple, Symbian i Windows mají jeno omezenou použitelnost

Platforma Programovou platformu definují tři komponenty Možnosti programovacího jazyka Použitý virtuální stroj Použité knihovny Aplikace komunikuje se systémem prostřednictvím knihovny Celý program interpretuje virtuální stroj Použitelnost platformy je závislá na dostupném HW Aplikace Knihovna P L A T F O R M Java Virtuální stroj Operační systém Hardware

Java ME – základní cíle Umožnit použití programovacího jazyka Java Použití v zařízeních s malou pamětí a pomalejším procesorem Respektovat velkou variabilitu zařízení Umožnit vývoj programů provozovatelných na všech zařízeních nezávisle na odlišnostech jejich hardwaru Umožnit připojení těchto zařízení k síti (wireless Java)

Konfigurace Java ME = Sada nástrojů, specifikací a technologií pro vývoj aplikací pro malá zařízení Značná variabilita zařízení si vynutila definici dvou konfigurací (podplatforem) CDC – Connected Device Configuration CLDC – Connected Limited Device Configuration Konfigurace specifikují minimální HW požadavky umožňující provoz příslušné (pod)platformy Všechny požadavky jsou povinné, neexistují volitelné možnosti (options)

Paměť a její rozlišení Požadavky na paměť patří mezi základní Vzhledem k charakteru zařízení se rozlišují dva druhy pamětí: Pevná (non-volatile) – nemaže se po skončení programu (ROM, EEPROM, …) Proměnná (volatile) (většinou RAM)

Java Card Je o něco starší, narodila se v roce 1997 Je určena pro čipové karty – nejmenší zařízení programovatelná v jazyku Java Typicky 32 – 64 KB EEPROM, 4 – 8 KB RAM, Používá se např. v kartách VISA

CLDC – Connected Limited Device Conf. Požadavky verze 1.1: Minimálně 192, z toho: Min 160 KB pevné pro základní knihovnu a VM Min 32 KB proměnné pro běh programu a objekty 16bitový nebo 32bitový procesor Připojení do sítě Nízká spotřeba – často bateriový provoz Typičtí představitelé: Mobilní telefony a pagery Video a audio systémy Navigační systémy Mobilní čtečky čárových kódů

CDC – Connected Device Configuration Požadavky: 32bitový procesor Min. 512 KB paměti pro vlastní Javu Min. 256 KB paměti pro alokaci paměti za běhu Plná funkcionalita virtuálního stroje Připojení k síti (často rychlé a trvalé) Oproti CLDC již podporuje náročnější funkce Serializace Reflexe Weak refernce JNI (Java Native Interface)

J2SE × J2ME J2SE CDC CLDC

CVM – Compact Virtual Machine Určen pro konfiguraci CDC Plná podpora Java 2 verze 1.3 Specifika Přenositelný Optimalizovaný na využití ROM Upravený správce paměti (Garbage Collector) Minimalizuje průměrný čas zdržení (real-time) Optimalizovaný na menší paměť Malá režie se správou tříd Zpočátku neimplementoval hot-spot ani JIT compiler Poskytuje rozhraní a podporu pro RTOS (Real Time Operating System)

KVM – Kilobyte Virtual Machine Navržen pro méně výkonné procesory 16bitové nebo 32bitové Od 25 MHz Malé požadavky na paměť (50 – 80 KB) Vysoce přenositelný, modulární a přizpůsobitelný Maximálně rychlý a kompletní Napsaný v jazyku C (24 000 řádek kódu) => snadno přenositelný na jakoukoliv platformu, pro níž existuje překladač jazyka C (prakticky všechny)

KVM – Verifikace Standardní přístup: zkontrolovat korektnost třídy při jejím zavedení (class loader) Časově a paměťově náročné (samotná verifikace spotřebuje 25 – 110 KB) CLDC nechává většinu práce vykonat při překladu Využívá omezený přístup k zařízení Využívá absenci některých konstrukcí (reflexe, rmi) Po překladu se nejprve provede preverifikace – při ní se do souboru .class doplní informace usnadňující verifikaci za běhu programu KVM pak provede jen nejnutnější verifikaci navíc usnadněnou dodatečnými informacemi

KVM – Omezení KVM neimplementuje následující rysy: Datové typy double a float (v příští verzi budou) Finalizace (Třída Object neobsahuje metodu finalize) Většinu výjimek typu Error (ponechává pouze 3) JNI (Java Native Interface – tj. neumožňuje zavádět za běhu programy napsané v nativním kódu) Reflexi, serializaci a RMI (Remote Method Invocation) Skupiny vláken (thread groups) a démony Slabé odkazy (weak references) Uživatelsky definované zavaděče tříd (class loaders)

Profily Doplňují konfigurace Umožňují horizontální oslovení trhu (různé možnosti stejného zařízení) Přidávají další třídy – jimi je profil definován Cíl: zpřístupnit nadstavbové funkce Specifické pro daný typ zařízení Oslovující speciální trh Profil může být nadstavbou nad jiným profilem Je možné implementovat několik profilů zároveň

Profily pro CDC Foundation Profile – základ ostatních profilů Zahrnuje většinu tříd jádra Java 2 verze 1.3 RMI Profile Přidává knihovnu J2SE RMI Personal Basis Profile – specifikace se dotahuje Přidává základní GUI V jednom okamžiku lze mít otevřené jediné okno Personal Profile – specifikace se dotahuje Umožňuje současné zobrazení několika oken Game Profile – specifikace ještě nejasná Neví se ani, zda bude založen na Foundation Profile

Profily pro CLDC Mobile Information Device Profile (MIDP) Nejznámější profil J2ME Primárně je zaměřen na mobilní telefony Přidává jednoduché UI respektující jejich omezení Přidává práci v síti založenou na HTTP 1.1 Přidává schopnost pracovat s lokální trvalou pamětí (lokální databáze pro uchování dat mezi zapnutími) PDA Profile (PDAP) Oproti MIDP počítá s větší obrazovka a větší pamětí Nabízí propracovanější UI Umožní lépe využívat možnosti operačního systému Hlavní profil pro menší (=méně výkonné) kapesní počítače

Historie MIDP Původní verze 1.0 byla velmi omezená Pracovala pouze s celými čísly Pracovala s velmi omezenou obrazovkou a ovládáním Verze 2.0 vyžaduje CLDC 1.1 Přidávala čísla v plovoucí čárce Přidávala řadu grafických možností pro hry Přidala možnost využití multimédií Verze 3.0 Zaměřená spíše na praktické aplikace Umožňuje sdílení knihoven mezi jednotlivými programy Aplikace mohou běžet souběžně a vzájemně spolu komunikovat

Přehled platforem Javy

Konfigurace a profily J2ME Toto nás nyní zajímá Personal Profile MIDP Mobile Information Device Profile PDAP Personal Digital Assistant Profile Personal Basis Profile RMI Profile Game Profile Foundation Profile ? CLDC Library Connected Limited Device Configuration CDC Library Connected Device Configuration KVM Kilobyte Virtual Machine CVM Compact Virtual Machine

Shrnutí Platformu definuje J2ME má dvě podplatformy: CDC a CLDC Jazyk Virtuální stroj Knihovna J2ME má dvě podplatformy: CDC a CLDC Každá má svůj virtuální stroj: CVM a KVM Pro každou je definována řada profilů Nejpropracovanější a v současné době nejpoužívanější je MIDP pro platformu CLDC

Java ME – MIDP Mobile Information Devices Profile

Základní požadavky na HW a OS 1/2 Obrazovka minimálně 96×54 bodů, stačí 1 bit Klávesnice (jednoruční či dvouruční) či touch screen Paměť: 160 KB pevné pro MIDP komponenty 32 KB proměnné pro Java runtime 8 KB pevné pro trvale uchovávaná data Obousměrné připojení k síti

Základní požadavky na HW a OS 2/2 Další požadavky na operační systém: Umožnit plánování procesů Umožnit ošetření výjimek Umožnit zpracovat přerušení Schopnost provozovat JVM (přesněji KVM) Umožnit na displeji bitmapovou grafiku

CLDC zahrnuje: java.lang java.util java.io javax.microedition.io Chybí podpora reflexe a plovoucí čárky java.util Třídy Calendar, Date, Enumeration, HashTable, Random, Stack, Vector a potřebné výjimky java.io Základní proudové vstupně výstupní operace bez souborů, vyrovnávacích pamětí (buffer) a práce s objekty. javax.microedition.io Třídy a rozhraní z Generic Connection Framework, jenž poskytuje jednodušší a jednotnější prostředí pro komunikaci s externími zařízeními.

Aplikace nad profilem MIDP Jednotlivé aplikace jsou označovány jako MIDlety Přeložené třídy lze sbalit (package) do souboru JAR doprovázeného textovým souborem JAD (Java Application Descriptor) Jedna dvojice JAR&JAD může obsahovat několik midletů – skupina bývá označována jako suita Aplikace z jedné suity spolu mohou sdílet některé prostředky a vyměňovat si data

MIDP řeší: Správu životního cyklu aplikace Balíček javax.microedition.midlet Umí aplikaci spustit, pozastavit, oživit a ukončit Uživatelské rozhraní a události Balíček javax.microedition.lcdui Obsahuje třídy a rozhraní pro komponenty GUI rozhraní Ukládání dat v zařízení Balíček javax.microedition.rms Správa záznamově orientované databáze Připojení k síti Doplňuje javax.microedition.io o HTTP protokol

Použité balíčky //Společný balík všech dnešních programů package workshop; //Užitečné pomocné třídy z J2SE (zestručněné) import java.util.*; //Vstup a výstup prostřednictvím datových proudů import java.io.*; //MIDP aplikace a její interakce s prostředím import javax.microedition.midlet.*; //API pro tvorbu UI v MIDP aplikacích import javax.microedition.lcdui.*; //Record Management Systém – trvalé uložení dat //mezi jednotlivými spuštěními aplikace import javax.microedition.rms.*; //Rozšíření podpory sítí pro MIDP import javax.microedition.io.*;

Vývojová prostředí Java Platform Micro Edition Software Development Kit 3.0 NetBeans + Mobility Pack

Různé emulátory 1/2 Všechny mají spuštěn tentýž program

Různé emulátory 2/2 Textový program vyměněn za grafický

Sun ONE Studio 4 ME (ukázka) 3/3

MIDlet

Životní cyklus aplikace – MIDletu Start Aplikace v profilu MIDP – MIDlet Po vytvoření svého objektu MIDlet čeká, až jej systém aktivuje Aktivní může být pouze jeden MIDlet Aktivní MIDlet může skončit nebo se opět vrátit do čekajícího stavu Ukončit je možno i čekající MIDlet Změnu stavu může MIDlet vyvolat sám Může ji vyvolat i jiný program zavoláním příslušné metody Čekající Aktivní Ukončený

Konstrukce MIDletu Potomek javax.microedition.midlet.MIDlet Třída MIDlet definuje metody, jejichž voláním je MIDlet upozorněn, že je převáděn do jiného stavu Metody slouží hlavně k alokaci a opětnému uvolnění systémových prostředků Metody jsou abstraktní => je nutno překrýt startApp() ® byl převeden do stavu aktivní pauseApp() ® bude převeden do stavu čekající destroyApp(boolean u) ® bude přev. do st. ukončený Je-li v destroyApp parametr u==false, může si MIDlet vybrat, zda bude opravdu končit

Přechody mezi stavy Start Program je řízený událostmi => z metod se musí program rychle vrátit, aby systém mohl opět převzít řízení Do příslušného stavu se program dostane až po opuštění metody Voláním uvedených metod umožní systém MIDletu optimálně alokovat a uvolňovat prostředky konstruktor startApp Čekající startApp pauseApp Aktivní destroyApp destroyApp destroyApp Ukončený

Přechodové metody 1/3 protected abstract void startApp() throws MIDletStateChangeException Alokuje prostředky pro aplikaci. Často přitom rozlišuje mezi prvním a následujícím spuštěním (tj. spuštěním po odchodu mezi čekající) Není-li v danou chvíli MIDlet schopen spuštění, vyvolá výjimku

Přechodové metody 2/3 protected abstract void pauseApp() Definuje chování MIDletu při odchodu mezi čekající Uvolňuje prostředky neobsahující informace nutné pro pokračování po opětném oživení Jednodušší aplikace mívají tuto metodu definovánu jako prázdnou

Přechodové metody 3/3 protected abstract void destroyApp(boolean unconditional) throws MIDletStateChangeException Uvolňuje všechny prostředky používané aplikací Parametr specifikuje, může-li aplikace požadavek na své ukončení odmítnout (=false) Odmítnutí požadavku na ukončení realizuje aplikace vyhozením výjimky

Přechody vyvolané MIDletem 1/2 Každá z přechodových metod má svého partnera, který slouží k tomu, aby MIDlet mohl požádat OS o převedení do požadovaného stavu sám Přechod do stavu Čekající public final void notifyPaused() Přechod do stavu Aktivní public final void notifyResume() Přechod do stavu Ukončená public final void notifyDestroyed() Při reakci na tato volání OS předpokládá, že MIDlet je pro přechod připraven, a proto již překryté abstraktní metody nevolá

Přechody vyvolané MIDletem 2/2 Metody žádající o převedení do jiného stavu je možno volat i z jiných balíčků, protože jsou deklarovány jako public Volání notifyResume nemůže MIDlet iniciovat sám (nepracuje, čeká), může jej však o to požádat jiný, aktivní MIDlet a aktivovat jej samotným zasláním zprávy Start Ukončený Aktivní Čekající notifyResume notifyPaused notifyDestroyed

Náš PrvniMIDlet Má implementované jen povinné metody překrývající abstraktní metody rodiče + konstruktor Metody pouze vypisují zprávy na standardní výstup MIDlet slouží jen k ověření funkce jednotlivých metod překrývajících abstraktní metody rodiče Lze z něj odvodit kdy je která metoda volána, kdy se vytváří nová instance a částečně i kdy se instance ruší

Aplikace DieMIDlet_1 Postupně vytvoříme program na házení kostkou Budeme simulovat běžnou hrací kostku Program bude ovládán dvěma příkazy: Next – realizuj další hod Quit – ukonči program V první etapě žádnou další funkcionalitu přidávat nebudeme

Struktura programu DieMIDlet_1

DieMIDlet_1 – realizace import javax.microedition.midlet.*; public class DieMIDlet_1 extends MIDlet { private static int m = 0; public DieMIDlet_1() { System.out.println("Midlet_1 Nr. "+ ++m +" constructed"); }// DieMIDlet_1() public void startApp() { System.out.println("Midlet_1 Nr. " + m + " activated"); new DieCast_1(this); //DieCast starts another thread }//startApp() public void pauseApp() {} public void destroyApp( boolean unconditional ) throws MIDletStateChangeException { System.out.println("Midlet_1 Nr. " + m + " destroyed"); notifyDestroyed(); }//public void destroyApp( boolean unconditional ) }//class DieMIDlet_1 extends MIDlet

Cvičení: Vlastní MIDlet Vytvořte prázdný MIDlet Do metod překrývajících abstraktní metody rodičovské třídy vložte příkazy k tisku do standardního výstupu Na konci těla metody startUp() vytvořte instanci třídy DieCast, která bude mít prozatím na starosti vlastní běh aplikace Upravte třídu podle vlastního uvážení

Cvičení: Zadání MIDletů pro JAR&JAD Otevřete okno pro nastavování vlastností projektu Ve stromu vlevo zadejte ve složce Application Descriptor položku MIDlets Stiskem Add otevřete okno pro přidání MIDletu Zadejte jako název MIDletu text, kterým chcete MIDlet označovat na obrazovce Ze seznamu vyberte třídu příslušného MIDletu.

Cvičení: Testování MIDletu Stiskem Shift+F11 sestavte (build) projekt Stiskem F6 svoji aplikaci spusťte Prověřte funkci MIDletu v emulátoru Zkuste si nastavit zarážky (breakpoints) a spustit program pod debuggerem Nechte si v okně Debugger Window nechat zobrazit hodnoty proměnných Zkuste program krokovat

Cvičení: Změna emulátoru Program je vhodné vyzkoušet pro různé konfigurace Změna emulátoru: Ve vlastnostech projektu zadejte nastavování platformy V textovém okně Device zadejte požadovaný emulátor Spusťte znovu svůj program

Suity

Koncepce MIDlety se mohou sdružovat do suit Zařízení nenahrává jednotlivé MIDlety, ale může nahrát celou jejich skupinu – suitu Při spuštění suity zařízení zobrazí nabídku MIDletů ve suitě, z níž uživatel vybere ten, jenž se spustí MIDlety ve suitě mohou sdílet třídy i paměť Bezpečnostní opatření: Permanentní paměť mohou sdílet POUZE MIDlety v rámci jedné suity; pro jiné je nepřístupná (ochrana proti virům)

MIDlet Suites Suita je reprezentována dvojicí souborů: JAR (Java Archive) obsahuje potřebný kód a data JAD (Java Application Descriptor) obsahuje pomocné informace JAD – textový soubor s řádky typu: název_atributu: hodnota_atributu Některé atributy jsou povinné (např. velikost JAR), jiné volitelné (povinné atributy dodává IDE samo) Tvůrce může definovat i své vlastní atributy MIDlet může hodnoty atributů zjišťovat za běhu

Parametry v JAD Vedle povinných a volitelných parametrů mohou být v souboru JAD i parametry uživatelské MIDlet je může přečíst a upravit dle nich své chování (lze je tak modifikovat bez nutnosti nového překladu) Parametry JAD zjišťuje metoda public final String getAppProperty(String key) Názvy parametrů jsou citlivé na velikost písmen Hodnoty parametrů mohou být i několikaslovné Nelze do nich vkládat Escape sekvence (např. "\n") přesněji: vkládat je lze, ale nereaguje na ně

Přidání parametru do JAD Otevřete okno s vlastnostmi projektu Ve stromu vlevo zadejte ve složce Application Descriptor položku Attributes Zadejte své jméno v atributu MIDlet-Vendor Stiskem Add otevřete okno, v němž zadáte vlastní atribut Potvrďte zadání stiskem OK

Přečtení parametru z JAD Vytvořte nový MIDlet jako kopii původního a nazvěte jej DieCast_1b Upravte metodu startApp tak, aby na standardní výstup vypisovala i vás jako dodavatele – např.: public void startApp() { String author = getAppProperty( "Author" ); System.out.println("Midlet_1b Nr. " + m + " from " + author + " started"); new DieCast_1(this); }//startApp() Přeložte a spusťte suitu Zkontrolujte standardní výstup druhého MIDletu

Low Level User Interface Nízkoúrovňové uživatelské rozhraní

Základní charakteristika Pod Low-Level rozhraním rozumíme skupinu tříd, jež mají na starosti přímé ovládání klávesnice a kreslení na obrazovku Tyto třídy jsou schopny kreslit Jednoduché grafické tvary (plné i obrysy) Čáry (obrysy a čáry umí plné či čárkované) Obdélníky (i se zakulacenými rohy) Elipsy a jejich výseče Text Obrázky Všechny jsou součástí balíku javax.microedition.lcdui

Získání displeje Vlákno, které chce, aby se jeho výstup zobrazoval, se musí vnutit na displej – požádá jej voláním void setCurrent( Displayable d ) Třída Displayable je (uměle) abstraktní – parametr je proto instancí některého jejího potomka Canvas (plátno) pro kreslení a low-level GUI Screen pro high-level GUI Screen se přímo nepoužívá – používají se potomci: Form pro formuláře s možností zadání čísel, textů a voleb Textbox pro zadání delších textů List pro výběr ze seznamu možností Alert pro asynchronní zprávu či upozornění

Třída Displayable Abstraktní třída, avšak bez abstraktních metod Definuje čtyři metody: boolean isShown() zjišťuje, jestli je objekt opravdu zobrazován void addCommand( Command cmd ) přidává další příkaz do seznamu void removeCommand( Command cmd ) vyjímá příkaz ze seznamu void setCommandListener( CommandListener l ) nastavuje posluchače, jenž definuje reakci na příkazy (nepřidává, nastavuje!) Na rozdíl od AWT či Swingu je posluchač společný pro všechny příkazy

Ovládání příkazy Protože naše třída kreslí, využijeme Canvas Canvas je abstraktní třída => musíme použít potomka Příkazy jsou objekty typu Command – konstruktor: Command(String label, int comType, int prior) label je návěští, které pojmenovává sadu příkazů comType je typ příkazu prior je relativní priorita příkazu vůči kolegům (0=max) Příkazy se postupně přidávají do seznamu Nejdůležitější (dle názoru systému) většinou systém umístí tak, aby byly co nejsnáze dostupné

void commandAction(Command c, Displayable d) Posluchači Posluchač musí implementovat rozhraní CommandListener Posluchač nemusí být v samostatné třídě, třída může zároveň fungovat jako posluchač CommandListener vyžaduje implementaci metody void commandAction(Command c, Displayable d) Vzhledem k parametrům metody může jeden posluchač sloužit několika pánům

DieCast_1 1/2 package workshop; import java.util.*; import javax.microedition.lcdui.*; import javax.microedition.midlet.*; class DieCast_1 extends ShowDie_1 //extends Canvas implements CommandListener { private static Command cmdQuit; private static Command cmdNext; private static MIDlet midlet; DieCast_1( MIDlet midlet ) { Display.getDisplay( midlet ).setCurrent( this ); this.midlet = midlet; cmdQuit = new Command( "Quit", Command.EXIT, 1); addCommand( cmdQuit ); cmdNext = new Command( "Next", Command.OK, 0); addCommand( cmdNext ); setCommandListener( this ); }//DieCast_1( MIDlet midlet )

DieCast_1 2/2 public void commandAction(Command c, Displayable d){ if( c == cmdQuit ) { //Leaving the program try{ midlet.destroyApplication( true ); } catch( Exception e ) { e.printStackTrace(); } } else if( c == cmdNext ) { //Next die cast cast(); }//protected void keypressed( int code ) private static final int MaxN = 9; private static Random rnd = new Random(); int cast() {//Uses inherited n for the just casted number n = (rnd.nextInt()&0X7fffffff) % MaxN + 1; repaint(); //Show the new cast ... return n; //... and return it }//int cast() }//class DieCast_1 extends ShowDie_1

Třída Canvas – vstup z klávesnice Canvas umí reagovat i na jednotlivé klávesy. K tomu použijeme metody: Po stisku klávesy vyvolá systém metodu protected void keyPressed(int keyCode) Po puštění klávesy vyvolá systém metodu protected void keyReleased(int keyCode) Při zadání kódu funkcí autorepeat vyvolá systém metodu protected void keyRepeated(int keyCode) Klávesnice jednotlivých zařízení se velmi liší Povinné jsou jen klávesy "0" – "9", "*" a "#" (chybí "clear") Některé klávesnice mají "joystick" Definováno 9 akcí, které výrobce namapuje Můžete reagovat na kód klávesy nebo na přiřazenou akci

Třída Canvas – kódy × akce Kódum odpovídají konstanty KEY_NUM0 – KEY_NUM9, KEY_POUND (#) a KEY_STAR (*) Akcím odpovídají konstanty UP, DOWN, LEFT, RIGHT FIRE GAME_A, GAME_B, GAME_C, GAME_D Akci přiřazenou klávese s daným kódem zjistíme pomocí int getGameAction(int keyCode) Kód klávesy, jíž je přiřazena akce, zjistíme pomocí int getKeyCode(int gameAction)

DieMIDlet_2 – rozšíření Umožní "hodit kostkou" prostřednictvím stisku klávesy FIRE Vytvoříme kostku jež umožní podvádět – na stisk předem definované klávesy umožní: 0 – povolí, resp. zakáže hození nuly 2–9 – nastaví dané číslo jako nejvyšší hoditelné číslo šipka nahoru – zadá házení pouze horní poloviny čísel šipka dolů – zadá házení pouze spodní poloviny čísel * (hvězdička) – padají čísla 1 – 9

DieCast_2 – startCast public class DieCast_2 extends ShowDie_1 implements CommandListener { private static DieCast_2 me; private static DieMIDlet_2 midlet; private static Command cmdQuit; private static Command cmdNext; private DieCast_2() { cmdQuit = new Command( "Quit", Command.EXIT, 1); cmdNext = new Command( "Next", Command.OK, 0); addCommand( cmdQuit ); addCommand( cmdNext ); setCommandListener( this ); }//DieCast_2( MIDlet midlet ) static void startCast( DieMIDlet_2 midlet ) { if( me == null ) me = new DieCast_2(); super( Display.getDisplay( midlet ) ); this.midlet = midlet; Display.getDisplay( midlet ).setCurrent( me ); }//static void startCast( DieMIDlet_2 midlet )

DieCast_2 – cast private static Random rnd = new Random(); private static int MinN = 1; //Initioal minimum private static int MaxN = 6; //Initioal maximum private static int min = MinN; //Actual minimum private static int max = MaxN; //Actual maximum private static int mmm = max - min + 1 //Interval int cast() { n = (rnd.nextInt()&0X7fffffff) % mmm + min; repaint(); //Repaint the canvas by new die return n; }//int cast()

DieCast_2 – keyPressed protected void keyPressed( int keyCode ) { switch( getGameAction(keyCode) ) { case FIRE: cast(); break; case UP: min = MaxN/2; max = MaxN; break; //High # case DOWN: min = MinN; max = MaxN/2; break; //Low # default: switch( keyCode ) { case KEY_NUM0: //Switch permission of the value 0 min = MinN ^= 1; break; case KEY_NUM2: //Set the max allowed value case KEY_NUM3: case KEY_NUM4: case KEY_NUM5: case KEY_NUM6: case KEY_NUM7: case KEY_NUM8: case KEY_NUM9: min = MinN; max = MaxN = (keyCode - KEY_NUM0); }//switch( keyCode ) }//switch action mmm = max – min + 1; }//protected void keyPressed( int keyCode )

Třída Canvas – překreslování Abstraktní – potomci musí překrýt abstraktní metodu void paint( Graphics g ) Metodu paint volá systém, když se rozhodne překreslit obrazovku Program žádá o překreslení plátna voláním metody final void repaint() O překreslení části plátna žádáme voláním metody final void repaint(int x, int y, int w, int h) Okamžité překreslení (tj. provedení všech čekajících příkazů repaint) zařídíte voláním final void serviceRepaints()

Canvas – další užitečné metody int getHeight() Vrací výšku obrazovky v bodech int getWidth() Vrací šířku obrazovky v bodech protected void hideNotify() Je volána systémem po odebrání displeje (můžeme zde např. zastavit animaci) protected void showNotify() Je volána systémem před předáním displeje (můžeme zde např. opět spustit animaci)

Třída Graphics – kreslení a psaní Abychom mohli na plátno kreslit, potřebujeme nějaké kreslítko (grafický kontext) – k tomu slouží instance třídy Graphics Umožňuje: Kreslit základní geometrické tvary Úsečky Vyplněné a nevyplněné obdélníky Vyplněné a nevyplněné eliptické výseče Volit typ kreslené čáry Vykreslovat obrázky Psát texty s možností volby písem, jejich velikostí a řezů

Graphics – kreslení 3.4.2017 void drawLine(int x1, int y1, int x2, int y2) Nakreslí čáru mezi body [x1;y1] a [x2;y2] void drawRect(int x, int y, int w, int h) void fillRect(int x, int y, int w, int h) Nakreslí (draw), resp. vyplní(fill) obdélník s levým horním rohem v [x;y], široký w bodů a vysoký h bodů void drawArc(int x, int y, int w, int h, int s, int u) void fillArc(int x, int y, int w, int h, int s, int u) Nakreslí, resp. vyplní část elipsy vepsané do obdélníku {x;y;w;h} s počátkem v úhlu s a středovým úhlem u l

Graphics – barvy Nerozlišuje se barva popředí a pozadí – pracuje se pouze s barvou, kterou se kreslí int getColor() Vrátí barvu kreslení ve formátu 0xRRGGBB void setColor( int RGB ) Nastaví barvu zadanou ve formátu 0xRRGGBB Barvy je možno zadávat i zjišťovat po komponentách int getGrayScale() void setGrayScale( int level ) Zjistí, resp. nastaví úroveň šedi jako číslo 0–255 (funguje i u barevných displejů)

ShowDie_1 1/3 public class ShowDie_1 extends Canvas { private static final int CMASK = 0xFFFFFF; //Color mask protected static int n; //Casted number //maxX,maxY = size of display; max = size of die private int maxX, xr, x0, dx; //[xr;yr] top left corner of die private int maxY, yr, y0, dy; //[x0;y0] pos.of top left point private int dd, max; //dx,dy = offset of next point //dd = diameter of point private Graphics g; private int color = 0xFFFF00; //Initial color ShowDie_1( Display display ) { System.out.println("ShowDie_1"); maxX = getWidth(); maxY = getHeight(); max = Math.min( maxX, maxY ) - 4; xr = (maxX - max) / 2; yr = (maxY - max) / 2; x0 = xr + max / 10; y0 = yr + max / 10; dx = 3 * max / 10; dy = 3 * max / 10; dd = 2*max/10; }//ShowDie_1( Display display )

ShowDie_1 2/3 public void paint( Graphics g ) { g.setColor( color ^= CMASK ); //Clear last cast g.fillRect( 0, 0, maxX, maxY ); // ... by inverted color g.setColor( color ^= CMASK ); //Prepare color for die side g.fillRect( xr, yr, max, max ); //Paint the empty die side g.setColor( color ^= CMASK ); //Prepare color for points this.g = g; //Remember the Graphics object for L_# methods switch( n ) { //Paint the points case 1: L_0(y0); L_2(y0+dy); L_0(y0+dy+dy); break; case 2: L_4(y0); L_0(y0+dy); L_1(y0+dy+dy); break; case 3: L_4(y0); L_2(y0+dy); L_1(y0+dy+dy); break; case 4: L_5(y0); L_0(y0+dy); L_5(y0+dy+dy); break; case 5: L_5(y0); L_2(y0+dy); L_5(y0+dy+dy); break; case 6: L_5(y0); L_5(y0+dy); L_5(y0+dy+dy); break; case 7: L_5(y0); L_7(y0+dy); L_5(y0+dy+dy); break; case 8: L_7(y0); L_7(y0+dy); L_5(y0+dy+dy); break; case 9: L_7(y0); L_7(y0+dy); L_7(y0+dy+dy); break; }//switch }//public void paint( Graphics g )

ShowDie_1 3/3 private void L_0( int y ) { } //L_0 = . . . g.fillArc( x0+dx+dx, y, dd, dd, 0, 360 ); } //L_1 = . . O private void L_2( int y ) { g.fillArc( x0+dx, y, dd, dd, 0, 360 ); } //L_2 = . O . private void L_4( int y ) { g.fillArc( x0, y, dd, dd, 0, 360 ); } //L_4 = O . . private void L_5( int y ) { g.fillArc( x0, y, dd, dd, 0, 360 ); g.fillArc( x0+dx+dx, y, dd, dd, 0, 360 ); } //L_5 = O . O private void L_7( int y ) { g.fillArc( x0+dx, y, dd, dd, 0, 360 ); g.fillArc( x0+dx+dx, y, dd, dd, 0, 360 ); } //L_7 = O O O }//public class ShowDie_1 extends Canvas

High Level User Interface Uživatelské rozhraní vyšších hladin

Základní charakteristika Pod High-Level rozhraním rozumíme skupinu tříd, jež mají na starosti "formulářový vstup": Zadání hodnot textových, číselných, "datumových" Možnost výběru jedné z několika možností Možnost nastavení či zrušení dané volby Všechny jsou součástí balíku javax.microedition.lcdui

Třída Form – formulář Vedle nabídek realizovaných instancemi třídy Command používáme i jiné způsoby zadání dat Hlavním prostředkem jsou instance třídy Form – ty vedle příkazů umožňují: Přímé zadání textových, číselných a "datumových" hodnot Zadání číselných hodnot pomocí stupnic Nastavování voleb Nastavování hodnot přepínačů Dalšími třídami pro zadání a editaci dat jsou TextBox pro zadávání a editaci rozsáhlejších textů List pro výběr jedné či více možností ze seznamu Tyto třídy si však v tomto úvodu neukážeme

Objekty umístitelné do formuláře Na formulář se umísťují položky = instance Item Item je abstraktní – používají se její potomci: TextField – zadání textových a/nebo číselných hodnot (umožňuje zadat typ vstupu: obecný text, číslo, heslo, telefon, URL adresa, e-mailová adresa, vlastní maska) DateField – zadání dat ("datumů") – pro snazší zadání často nabízí kalendář Gauge – zadání číselných hodnot pomocí stupnice ImageItem – obrázková položka (jen informační, neumožňuje nic zadat) StringItem – řetězcová položka (jen informační) ChoiceGroup – nastavení přepínače, resp. voleb (jestli se jedná o přepínač či volby se zadá při volání konstruktoru)

Vložení položek do formuláře Položky se vkládají pomocí metod : append( Item item ) vloží na konec položku item append( String str) vloží na konec řetězec str append( Image image ) vloží na konec obrázek image insert(int itemNum, Item item) vloží položku item před položku s indexem itemNum Položku je možno vyjmout příkazem: delete(int itemNum)vyjme položku číslo itemNum Položku je nahradíme příkazem: set(int itemNum, Item item) nahradí položku s indexem itemNum položku item

Zadání a aktualizace dat Zajímavé události zachytává posluchač změn, který se nastavuje příkazem: void setItemStateListener( ItemStateListener itemStateListener ) Objekt typu ItemStateListener musí implementovat metodu: itemStateChanged(Item item) která obdrží odkaz na položku, u níž došlo k nějaké změně Metoda nejenom zjišťuje obsah položky item, ale může přitom nastavovat i parametry jiných položek

DieMIDlet_3 – rozšíření Umožní uživateli zadávat parametry kostky s využitím High-Level rozhraní Bude možno nastavit: Barvu kostky zadáním barevných složek, z nichž se bude barva skládat Tvar obrazců na kostce – bude možno zvolit: Kruh Čtvercový blok Kružnici Čtverec Nejnižší hoditelné číslo s využitím stupnice Nejvyšší hoditelné číslo přímým zadáním hodnoty

Struktura programu

Setup_3 1/4 package workshop; import javax.microedition.lcdui.*; class Setup_3 extends Form implements ItemStateListener { private static Setup_3 me = null; private static DieCast_3 dc; private ChoiceGroup cgrColor; private ChoiceGroup cgrShape; private Gauge gauMin; private TextField txfMax; private String[] cName = { "Red", "Green", "Blue" }; private String[] sName = { "Disk", "Block", "Rectangle", "Circle" };

Setup_3 2/4 private Setup_3(DieCast_3 dc) { super("Setup"); //The only Form constructor has String param. this.dc = dc; addCommand( dc.cmdOK ); addCommand( dc.cmdQuit ); setCommandListener( dc ); cgrColor = new ChoiceGroup( "Color", Choice.MULTIPLE, cName, null ); cgrShape = new ChoiceGroup( "Shape", Choice.EXCLUSIVE, sName, null ); gauMin = new Gauge( gauMinLabel(), true, dc.max, dc.min ); txfMax = new TextField( txfMaxLabel(), ""+dc.max, 2, TextField.NUMERIC ); append( cgrColor ); append( cgrShape ); append( gauMin ); append( txfMax ); setItemStateListener( this ); }//private Setup_3()

Setup_3 3/4 public void itemStateChanged( Item item ) { if( item == cgrColor ) { int color = 0; for( int i=0; i < 3; i++ ) { color <<= 8; color |= cgrColor.isSelected(i) ? 0xFF : 0; } ShowDie_3.color = color; }else if( item == cgrShape ) { int i; ShowDie_3.drawer = ShowDie_3.drawers[i=cgrShape.getSelectedIndex()]; }else if( item == gauMin ) { dc.min = gauMin.getValue(); gauMin.setLabel(gauMinLabel()); txfMax.setLabel(txfMaxLabel()); }else if( item == txfMax ) { dc.max = Integer.parseInt( txfMax.getString() ); }else throw new IllegalArgumentException(); }//void ItemStateChanged( Item item )

Setup_3 4/4 private String gauMinLabel() { return "From [0-" + dc.max + "]: " + dc.min; }//private String gauMinLabel() private String txfMaxLabel() { return "To [" + dc.min + "-" + dc.MaxN + "]: " + dc.max; }//private String txfMaxLabel() static void setup(DieCast_3 dc) { if( me==null ) { me = new Setup_3( dc ); } Display.getDisplay( dc.midlet ).setCurrent( me ); }//static void setup() }//class Setup_3 extends Form implements ItemStateListener

ShowDie_3 1/4 package workshop; import java.util.*; import javax.microedition.lcdui.*; public class ShowDie_3 extends Canvas { static int color = 0xFFFF00; final static int COLOR_0 = 0xFFFF00; private static final int CMASK = 0xFFFFFF; protected static int n; private int maxX, xr, x0, dx; private int maxY, yr, y0, dy; private int dd, max; private static Graphics g;

ShowDie_3 2/4 static interface Drawer { void draw(int x, int y, int w, int h); }//private static interface Drawerdrawer static Drawer drawers[] = { new Drawer(){ //Disk public void draw(int x, int y, int w, int h){ g.fillArc(x, y, w, h, 0, 360); }}, new Drawer(){ //Block g.fillRect(x, y, w, h); }}, new Drawer(){ //Rectangle g.drawRect(x, y, w, h);}}, new Drawer(){ //Circle g.drawArc(x, y, w, h, 0, 360 ); }}, }//static Drawer drawers[] static Drawer drawer = drawers[0];

ShowDie_3 3/4 ShowDie_3() { System.out.println("ShowDie_1"); maxX = getWidth(); maxY = getHeight(); max = Math.min( maxX, maxY ) - 4; xr = (maxX - max) / 2; yr = (maxY - max) / 2; x0 = xr + max / 10; y0 = yr + max / 10; dx = 3 * max / 10; dy = 3 * max / 10; dd = 2*max/10; }//ShowDie_1() public void paint( Graphics g ) { g.setColor( color ^= CMASK ); g.fillRect( 0, 0, maxX, maxY ); g.fillRect( xr, yr, max, max ); this.g = g; switch( n ) { case 1: L_0(y0); L_2(y0+dy); L_0(y0+dy+dy); break; case 2: L_4(y0); L_0(y0+dy); L_1(y0+dy+dy); break; case 3: L_4(y0); L_2(y0+dy); L_1(y0+dy+dy); break; case 4: L_5(y0); L_0(y0+dy); L_5(y0+dy+dy); break; case 5: L_5(y0); L_2(y0+dy); L_5(y0+dy+dy); break; case 6: L_5(y0); L_5(y0+dy); L_5(y0+dy+dy); break; case 7: L_5(y0); L_7(y0+dy); L_5(y0+dy+dy); break; case 8: L_7(y0); L_7(y0+dy); L_5(y0+dy+dy); break; case 9: L_7(y0); L_7(y0+dy); L_7(y0+dy+dy); break; } }//public void paint( Graphics g )

ShowDie_3 4/4 private void L_0( int y ) {} //L_0 = . . . private void L_1( int y ) { //L_1 = . . O drawer.draw( x0+dx+dx, y, dd, dd); }//private void L_1( int y ) private void L_2( int y ) { //L_2 = . O . drawer.draw( x0+dx, y, dd, dd); }//private void L_2( int y ) private void L_4( int y ) { //L_4 = O . . drawer.draw( x0, y, dd, dd); }//private void L_4( int y ) private void L_5( int y ) { //L_5 = O . O drawer.draw( x0, y, dd, dd); }//private void L_5( int y ) private void L_7( int y ) { //L_7 = O O O drawer.draw( x0+dx, y, dd, dd); }//private void L_7( int y )

Uchování hodnot mezi seancemi

Balík javax.microedition.rms RMS (Record Management System) umožňuje uložit data do trvalé paměti a opět je odtud načíst Uložená data mohou MIDlety v rámci suity sdílet – je to jediná možnost, jak si předávat informace MIDletům mimo suitu je tato paměť nepřístupná Data zůstanou zachována i po vypnutí zařízení Instance třídy RecordStore jsou jednoduché, záznamově orientované, pojmenované databáze Záznamy jsou identifikovány dle svých ID Operace probíhají prostřednictvím pole bajtů

RecordStore – operace s databází static String[] listRecordStores() vrátí seznam jmen databází, které jsou k dispozici static RecordStore openRecordStore(String recordStoreName, boolean createIfNecessary) Otevře (a případně vytvoří) databázi se zadaným názvem void closeRecordStore() – Uzavře danou databázi static void deleteRecordStore(String recordStoreName) Odstraní databázi se zadaným názvem String getName() – Vrátí název dané databáze int getVersion() Vrátí verzi dané databáze (verze se zvyšuje po každé změně obsahu) long getLastModified() – Vrátí systémový čas poslední modifikace int getSize() – Vrátí počet bajtů, které daná databáze zabírá int getSizeAvailable() Vrátí počet bajtů, o něž může databáze ještě narůst

RecordStore – operace se záznamy int getNumRecords() – Vátí počet záznamů v databázi int addRecord(byte[] data, int offset, int numBytes) Přidá do databáze nový záznam a vrátí jeho ID (atomická operace) byte[] getRecord(int recordId) Vrátí vektor bajtů s daty ze záznamu recordId int getRecord(int recordId, byte[] buffer, int offset) Naplní vektor buffer od pozice offset daty ze záznamu recordId, Vrátí počet přenesených bajtů void setRecord(int ID, byte[] data, int off, int nb ) Nahradí záznam ID záznamem tvořeným nb bajty od pozice data[off] void deleteRecord(int recordId) – Odstraní záznam recordId int getRecordSize(int recordId) – Vrátí velikost záznamu RecordEnumeration enumerateRecords(RecordFilter filter, RecordComparator comparator, boolean keepUpdated) Vrátí iterátor pro procházení vybraných záznamů ve specifikovaném pořadí

Potřebné třídy z balíku java.io Protože se s databází komunikuj prostřednictvím vektorů bajtů, je potřeba zprostředkovatel Používají se instance tříd z java.io Pro zápis se používá "cesta" DataOutputStream ® ByteArrayOutputStream ® RecordStore Pro čtení se používá naopak "cesta" RecordStore ® ByteArrayInputStream ® DataInputStream

DieMIDlet_4 – rozšíření Bude si pamatovat nastavené hodnoty i po vypnutí

Metoda loadSetup 1/2 RecordStore rs; byte[] input; static void loadSetup() { RecordStore rs; byte[] input; ByteArrayInputStream bais; DataInputStream dis; try { rs = RecordStore.openRecordStore( RS_NAME, false ); }catch( RecordStoreNotFoundException e ) { DieCast_4.reset(); saveSetup(); return; }catch( Exception e ) { DieCast_4.reset(); return; } try { if( (input = rs.getRecord( 1 )) == null ) throw new NullPointerException(); try { rs.closeRecordStore(); RecordStore.deleteRecordStore( RS_NAME ); }catch( Exception e2 ) { return;

Metoda loadSetup 2/2 bais = new ByteArrayInputStream( input ); dis = new DataInputStream( bais ); try { DieCast_4.min = dis.readInt(); DieCast_4.max = dis.readInt(); DieCast_4.drawer = DieCast_4.drawers[ Setup_4.drawerID = dis.readInt() ]; ShowDie_3.color = dis.readInt(); } catch( Exception e ) { DieCast_4.reset(); return; System.out.println("loaSetup: setup loaded"); }//static void loadSetup()

Metoda saveSetup 1/3 static void saveSetup() { ByteArrayOutputStream baos = new ByteArrayOutputStream(); DataOutputStream daos = new DataOutputStream( baos ); byte[] output; RecordStore rs; try { daos.writeInt( DieCast_4.min ); daos.writeInt( DieCast_4.max ); daos.writeInt( Setup_4.drawerID ); daos.writeInt( ShowDie_3.color ); DieCast_4.drawer = DieCast_4.drawers[Setup_4.drawerID]; }catch( Exception e ) { return; } output = baos.toByteArray();

Metoda saveSetup 2/3 try { rs = RecordStore.openRecordStore( RS_NAME, false ); }catch( RecordStoreNotFoundException e ) { rs = RecordStore.openRecordStore( RS_NAME, true ); }catch( Exception e2 ) { return; } //Create the first (and only) record try{ rs.addRecord( output, 0, output.length ); }catch( Exception e2 ) { }catch( Exception e ) {

Metoda saveSetup 3/3 try { rs.setRecord( 1, output, 0, output.length ); }catch( Exception e ) { rs.closeRecordStore(); RecordStore.deleteRecordStore( RS_NAME ); }catch( Exception e2 ) { return; } System.out.println("saveSetup: setup saved, rs closed"); }//static void saveSetup()

K O N E C