Android Rita och touch events

Relevanta dokument
Android La sa va rden fra n sensorer

Laboration 3 GUI-programmering

TDDI82 - Projekt. Christoffer Holm. Institutionen för datavetenskap (IDA)

Föreläsning 4. Klass. Klassdeklaration. Klasser Och Objekt

Lab5 för prgmedcl04 Grafik

F8 - Arv. ID1004 Objektorienterad programmering Fredrik Kilander

Det är principer och idéer som är viktiga. Skriv så att du övertygar rättaren om att du har förstått dessa även om detaljer kan vara felaktiga.

Föreläsning 5-6 Innehåll. Exempel på program med objekt. Exempel: kvadratobjekt. Objekt. Skapa och använda objekt Skriva egna klasser

Tentamen i Objektorienterad modellering och design

Föreläsning 5-6 Innehåll

Laboration 1: Figurer i hierarki

Subklasser och arv Inledning till grafik (JFrame och JPanel). Något om interface. Objektorienterad programvaruutveckling GU (DIT011) Subklasser

TENTAMEN OOP

Arv och polymorfism i Java

Detta dokument är ett exempel, cirka andra hälften av en tentamen för TDA545 Objektorienterad programvaruutveckling

Föreläsning 2. Länkad lista och iterator

Idag. statiska metoder och variabler. private/public/protected. final, abstrakta klasser, gränssnitt, delegering. wrapper classes

Arv: Fordonsexempel. Arv. Arv: fordonsexempel (forts) Arv: Ett exempel. En klassdefinition class A extends B {... }

if (n==null) { return null; } else { return new Node(n.data, copy(n.next));

Tentamen. 2D4135 vt 2004 Objektorienterad programmering, design och analys med Java Torsdagen den 3 juni 2004 kl

OOP Objekt-orienterad programmering

Föreläsning 4 Innehåll. Abstrakta datatypen lista. Implementering av listor. Abstrakt datatypen lista. Abstrakt datatyp

KARLSTADS UNIVERSITET 12/8/09 informatik & datavetenskap Johan Öfverberg, Kerstin Andersson Laboration 4, ISG A04 och DVG A08 HT-09

TENTAMEN OOP

Tentamen FYTA11 Javaprogrammering

Två designmönster, MVC och Observer/Observable. Objektorienterad programvaruutveckling GU (DIT011)

Tentamen för kursen Objektorienterad programvaruutveckling GU (DIT010)

TDA550 Objektorienterad programvaruutveckling IT, forts. kurs Övning vecka 2

Programmering med Java. Grunderna. Programspråket Java. Programmering med Java. Källkodsexempel. Java API-exempel In- och utmatning.

Föreläsning 13 Innehåll

Föreläsning 3. Stack

TENTAMEN OOP

Det här dokumentet är till för att ge en översikt över ASP.NET MVC samt hur WCF Services används från.net applikationer.

Kompilering och exekvering. Föreläsning 1 Objektorienterad programmering DD1332. En kompilerbar och körbar java-kod. Kompilering och exekvering

Classes och Interfaces, Objects och References, Initialization

Dagens program. Programmeringsteknik och Matlab. Vad är arv? Vi ärver från GregorianCalendar. Kan vi bygga vidare på existerande klasser?

DAT043 - Föreläsning 7

Tentamen i Objektorienterad modellering och design Helsingborg

Tentamen Programmeringsteknik II Inledning. Anmälningskod:

Programmeringsteknik II - HT18. Föreläsning 6: Grafik och händelsestyrda program med användargränssnitt (och Java-interface) Johan Öfverstedt

UML. Objekt-orienterad programmering och design (DIT952) Niklas Broberg, 2016

Properties. Användbara metoder som kan anropas i propertychanged:

Exempel på användning av arv: Geometriska figurer

OOP Objekt-orienterad programmering

DI-institutionen Sid 1 av 6 Hans-Edy Mårtensson Sten Sundin

Tentamen i Objektorienterad programmering

TENTAMEN I PROGRAMMERING. På tentamen ges graderade betyg:. 3:a 24 poäng, 4:a 36 poäng och 5:a 48 poäng

Föreläsning 12. Länkade listor

Design Patterns. En kort introduktion

Föreläsning 2. Länkad lista och iterator

Android översikt. TDDD80 Mobila och sociala applikationer

public och private Obs: private inte skyddar mot access från andra objekt i samma klass.

Föreläsnings 11 - GUI, Händelsestyrda program, MVC

Föreläsning 8. Arv. Arv (forts) Arv och abstrakta klasser

Lektion Händelsehanterare

Innehåll. dynamisk bindning. och programmering CRC) u Arv, polymorfi och

Monday, November 16, Senaste Labben

Föreläsning 8 - del 2: Objektorienterad programmering - avancerat

F4. programmeringsteknik och Matlab

Lösningar till tentamen i EDAF25

Föreläsning 3. Stack

OOP Objekt-orienterad programmering

Föreläsning 2, vecka 6: Tillstånd i objektorienterade program (och mera interface)

Föreläsning 4. ADT Kö Kö JCF Kö implementerad med en cirkulär array Kö implementerad med en länkad lista

Detaljbeskrivning av Player

Introduktion. Klasser. TDP004 Objektorienterad Programmering Fö 2 Objektorientering grunder

Tentamen Programmeringsteknik II och NV2 (alla varianter) Skriv bara på framsidan av varje papper.

LÖSNINGSFÖRSLAG Programmeringsteknik För Ing. - Java, 5p

ID1004 Laboration 3, 5-6 November 2012

Lösningsförslag till exempeltenta 1

TDDE10 m.fl. Objektorienterad programmering i Java Föreläsning 7 Erik Nilsson, Institutionen för Datavetenskap, LiU

Tentamen Programmering fortsättningskurs DIT950

Vad är programmering Jonas Lindemann

Classes och Interfaces, Objects och References Objekt-orienterad programmering och design (DIT952) Niklas Broberg, 2016

2I1049 Föreläsning 5. Objektorientering. Objektorientering. Klasserna ordnas i en hierarki som motsvarar deras inbördes ordning

Inkapsling tumregler. Åtkomstmodifikatorer, instantiering, referenser, identitet och ekvivalens, samt klassvariabler. public och private

Rekursion. Att tänka rekursivt Att programmera rekursivt i Java Exempel. Programmeringsmetodik -Java 254

OOP Objekt-orienterad programmering

TDDD78 Viktiga begrepp, del 2

Arv. Fundamental objekt-orienterad teknik. arv i Java modifieraren protected Lägga till och modifiera metoder med hjälp av arv Klass hierarkier

Anmälningskod: Lägg uppgifterna i ordning. Skriv uppgiftsnummer (gäller B-delen) och din kod överst i högra hörnet på alla papper

ITK:P1 Föreläsning 4. Grafiska gränssnitt i Java. AWT-komponenter

Föreläsning 3: Händelsestyrda program och användargränssnitt

LÖSNINGSFÖRSLAG

Arv innebär att man skapar en ny klass (subklass) utifrån en redan existerande klass (superklass, basklass).

Objektinteraktion. Objektorienterad programmering Laboration 2. Syfte Att konstruera ett litet objektorienterat program med flera samverkande objekt.

Programmering. Scratch - grundövningar

Listor. Koffman & Wolfgang kapitel 2, avsnitt , och 2.9

public interface Skrivbar { void skriv(); } public class Punkt implements Skrivbar { public double x; public double y;

TENTAMEN PROGRAMMERING I JAVA, 5P SOMMARUNIVERSITETET

ID1004 Laboration 4, November 2012

Lösningsförslag till tentamen

Interface. Interface. Tobias Wrigstad (baserat på bilder från Tom Smedsaas) 3 december 2010

PROGRAMMERINGSTEKNIK TIN212

Labbinstruktioner för Java/Swing

SI-pass 4. Johan Brook och Jesper Persson. 25 september Diskutera och svara på om påståendena nedan är äkta sanningar eller listiga lögner.

Det är principer och idéer som är viktiga. Skriv så att du övertygar rättaren om att du har förstått dessa även om detaljer kan vara felaktiga.

Laboration A Objektsamlingar

Tentamen i Objektorienterad modellering och diskreta strukturer

Att prova på en enkel Applet och att lära sig olika sätt att hämta data från tangentbordet. Du får även prova på att skapa din första riktiga klass.

Transkript:

Android Rita och touch events Notera att detta endast är en introduktion och inte är fullständiga instruktioner. För att komma vidare på egen hand kan du följa de länkar till texter som anges. Rita på en View För att rita på en vy, View, behöver du skapa en subklass till View (eller någon subklass till View). Själva ritytan är ett objekt av typen Canvas, en målarduk där det är möjligt att rita geometriska figurer, bilder och liknande. Klassen Paint representerar en låda med verktyg för att rita; här kan du välja färg, tjocklek på linjer m.m. Ett exempel från projektet OnDrawExample, klassen BasicOnDrawView som ärver från View: public class BasicOnDrawView extends View { public BasicOnDrawView(Context context, AttributeSet attributes) { super(context, attributes); // Load an image from res/drawable Resources res = context.getresources(); androidicon = res.getdrawable(r.drawable.ic_launcher); private Paint mpaint = new Paint(); private Drawable androidicon; @Override protected void ondraw(canvas canvas) { // Get the current size of this view int w = this.getwidth(), h = this.getheight(); int offset = (h - w) / 2; // Background mpaint.setcolor(color.ltgray); canvas.drawpaint(mpaint); // Fill a rectangle mpaint.setcolor(color.blue); canvas.drawrect(0, offset, w, h - offset, rectpaint); // left, top, right, bottom // Draw an image (automatic scaling via "bounds" androidicon.setbounds(x, y, x+100, y+100); // left, top, right, bottom androidicon.draw(canvas); Notera att Du definierar vad som ska ritas genom att omdefiniera metoden ondraw. Vyn kommer att ritas om när systemet anser att det behövs (ex. när vyn visas efter att ha varit dold). Vill du din applikation ska kräva en omritning ska du inte anropa ondraw direkt utan view.invalidate(). Koordinaterna anger pixels. Koordinatsystemet för vyn har origo i övre vänstra hörnet (x ökar åt höger, y ökar nedåt(!)). Bilder måste finnas i projektmappen res/drawables. I konstruktorn ovan ser du hur bilden laddas in från filen. I ondraw ser du hur du ritar bilden.

När en bild ska ritas måste ange koordinater för övre-vänstra och nedre-högra hörnet (här: androidicon.setbounds( )). Bilden kommer automatiskt att skalas till den angivna storleken(!). Testkör projektet OnDrawExample. Notera hur lyssnaren till knappen anropar view.invalidate för att vyn uppdatera vyn. Ändra i BasicOnDrawView.onDraw så att färgen ändras eller så att andra figurer ritas. Prova att lägga till en ny bild (.png) och rita upp denna (bilden ska ligga i mappen res/drawable). Läs mer om hur man ritar i vyer på http://developer.android.com/training/custom-views/custom-drawing.html och http://developer.android.com/guide/topics/graphics/2d-graphics.html. Touch events Du kan fånga touch events, dvs. att användaren pekar på skärmen, genom att låta din aktivitet (Activity) eller din vy (View) implementera interfacet View.OnTouchListener. Varje gång användaren rör skärmen anropas din lyssnare och du kan avgöra vad det är för typ av händelse, se nedan. private class MyTouchListener implements View.OnTouchListener { @Override public boolean ontouch(view v, MotionEvent event) { int action = event.getaction(); switch(action) { case (MotionEvent.ACTION_DOWN): // To do... case (MotionEvent.ACTION_MOVE): case (MotionEvent.ACTION_UP): case (MotionEvent.ACTION_CANCEL): case (MotionEvent.ACTION_OUTSIDE): default: // The event is consumed Du måste också registrera lyssnaren till din aktivitetet eller vy, t.ex. i en konstruktor med this.setontouchlistener(new ytouchlistener()); Testkör projektet TouchEventExample. Ändra, i ScribbleView, så att en linje ritas om användaren drar fingret över skärmen, från den punkt där fingret sätts ned (ACTION_DOWN) till den punkt där fingret lämnar skärmen (ACTION_UP).

Tips: Spara punkten från event vid ACTION_DOWN men rita inte. Vid ACTION_UP ritar du en linje från den sparade punkten till den nya punkten (event.getx resp. event.gety). Använd canvas drawline(x1,y1,x2,y2,paint) för att rita. Gör ett enkelt ritprogram genom att spara varje ny linje i en lista (det finns en klass för en linje i filen ScribbleView) i en ArrayList. I ondraw loopar du igenom listan och ritar varje linje som sparats. Det finns ett lösningsförslag till denna uppgift längre fram i dokumentet. Ett enkelt spel, Snake Testkör projektet Snake som innehåller en enkel variant av spelet med Samma namn. Projektet är ganska omfattande, och du behöver inte förstå alla detaljer. Lite information. Klassen SnakeModel är en klass som innehåller listor som representerar ormens segment samt äpplen. Det är möjligt att starta, stoppa och pausa modellen samt ändra riktning. Klassen är en ren modell-klass, dvs. den beskriver tillståndet hos ormen, men inget om hur den ska ritas i en vy. Klassen SnakeView innehåller kod för att rita upp ormen i en vy (klassen är en subklass till View), samt för att animera ormen så att den rör sig. Det är också här det finns en lyssnare för touch events som används för att ändra riktning på ormen (pekar man på övre halvan av skärmen vänder ormen uppåt osv.). Lägg till att ett nytt äpple läggs ut varje gång ett tidigare äpple äts upp. Du behöver anropa SnakeModels metod addapple någonstans i metoden updateapples. Testa vad som händer om du i SnakeView ändrar värdet på movedelay något (vad representerar denna datamedlem)? Gester, ex. swipe Det finns klasser och interface som kan användas för att hantera gester, t.ex. GestureDetector.OnGestureListener. Dessa är dock något mer komplicerade att använda (vill du läsa mer se http://developer.android.com/training/gestures/index.html). Ett enkelt sätt att detektera om användaren sveper fingret över skärmen kan vara att använda en View.OnTouchListener och jämföra koordinaterna där fingret sätts ned med punkten där fingret släpps upp (MotionEvent.ACTION_DOWN respektive ACTION_UP). Gå tillbaka till projektet TouchEventExample. Skriv kod för att detektera om användaren drar fingret över skärmen horisontellt minst 100 pixels (t.ex.). Tips: jämför x-koordinaterna för finger upp och finger ned med det förutbestämda avståndet. Eventuellt behöver du beräkna ett absolutbelopp för sträckan, med Math.abs.

Försök använda samma idé för Snake, men nu för att detektera svep både horisontellt och vertikalt (lite knepigare logik). Ett förslag på lösning (för Snake) finns längre fram i detta dokument. Några svårare uppgifter (samarbeta gärna två och två) En del av dessa uppgifter kräver att du söker information på nätet alternativt frågar en lärare. Lägg till en menu med alternativ för att starta ett nytt spel (SnakeView.startAnimation) samt pausa och återuppta ett spel (pauseanimation resp. resumeanimation). Lägg till att ormen växer ett segment (lägg till en Point) då den äter ett äpple (detta gör du i klassen SnakeModel). Det är enklast att lägga till ett nytt segment i början av ormen (msnaketrail i klassen SnakeModel; lägg till i listan med msnaketrail.add(0, somenewpoint) ). Du behöver veta vilken riktning ormen rör sig i för att kunna beräkna den nya riktningen. Det finns förslag till en del av lösningen längre fram i detta dokument.

Lösningsförslag Ett enkelt ritprogram, Scribble Jag utgår här från projektet TouchEventExample och klassen ScribbleView. Notera att det redan finns en klass, Line, som sparar start och slutpunkten för en linje. I klassen ScribbleView Lägg till en datamedlem för en lista med linjer: private ArrayList<Line> thelines = new ArrayList<Line>(); Ändra metoden ondraw till att rita ut alla linjer i listan: public void ondraw(canvas canvas) { mpaint.setcolor(color.black); mpaint.setstrokewidth(3); for(line line : thelines) { canvas.drawline(line.x1, line.y1, line.x2, line.y2, mpaint); Ändra lyssnarklassens metod ontouch till: public boolean ontouch(view v, MotionEvent event) { int action = event.getaction(); switch (action) { case (MotionEvent.ACTION_DOWN): x = event.getx(); y = event.gety(); Log.i("TouchEventExample", "ontouch"); case (MotionEvent.ACTION_UP): Line line = new Line(x, y, event.getx(), event.gety()); thelines.add(line); invalidate(); // call ondraw Log.i("TouchEventExample", line.tostring()); default:

OnTouchListener för swipe i spelet Snake (SnakeView) private class SnakeTouchListener implements View.OnTouchListener { private float xdown, ydown, xup, yup; private final float MIN_DISTANCE = 100; @Override public boolean ontouch(view v, MotionEvent event) { int action = event.getaction(); switch(action) { case (MotionEvent.ACTION_DOWN): xdown = event.getx(); ydown = event.gety(); case (MotionEvent.ACTION_MOVE): case (MotionEvent.ACTION_UP): xup = event.getx(); yup = event.gety(); float deltax = xup - xdown; float deltay = yup - ydown; // Horizontal swipe? if(math.abs(deltax) > MIN_DISTANCE && Math.abs(deltaX) > Math.abs(deltaY)) { if(deltax > 0) { // Left to right snakemodel.setdirection(direction.east); else { snakemodel.setdirection(direction.west); // Vertical swipe? else if(math.abs(deltay) > MIN_DISTANCE) { if(deltay > 0) { // Downwards snakemodel.setdirection(direction.south); else { snakemodel.setdirection(direction.north); case (MotionEvent.ACTION_CANCEL): case (MotionEvent.ACTION_OUTSIDE): default: // The event is consumed

Lägga till ett segment till ormen Lägg till segmentet först i listan msnaketrail. Koordinaterna för den nya punkten är bl.a. beroende av vilken riktning ormen har. Förslag till hjälpmetod: private void growsnake() { // Add a new segment before the current head Point oldhead = msnaketrail.get(0); Point newhead = null; switch(mdirection) { case NORTH: newhead = new Point(oldHead.x, oldhead.y-1); case SOUTH: newhead = new Point(oldHead.x, oldhead.y+1); case WEST: newhead = new Point(oldHead.x-1, oldhead.y); case EAST: newhead = new Point(oldHead.x+1, oldhead.y); msnaketrail.add(0, newhead); Denna metod anropas sedan på lämpligt ställe i metoden SnakeModel.updateApples (om du vill att ormen ska växa då den äter ett äpple).