1. Nimm jetzt an unserem Uhans - 3. ADVENT - Gewinnspiel teil - Alle Informationen findest Du hier!

newbie 2D graphik

Dieses Thema im Forum "Android App Entwicklung" wurde erstellt von jim, 08.05.2010.

  1. jim, 08.05.2010 #1
    jim

    jim Threadstarter Android-Hilfe.de Mitglied

    Beiträge:
    74
    Erhaltene Danke:
    0
    Registriert seit:
    02.05.2010
    Hallo liebes Forum,

    ich habe mich nun durch "hello Android" gearbeitet und ein kleines Projekt angefangen. Ziel soll es sein eine Applikation zu erstellen welche einen Wert (m/s)entgegen nimmt und mit dem eingestellten Wert(Planet) verrechnet und ein Ball dann in der jeweiligen Geschwindigkeit fallen lässt. Ein Brett welcher mit der eingegebenen Geschwindigkeit über den Boden fährt soll diesen Ball auffangen. Wenn die Applikation startet können Werte eingegeben werden, nun möchte ich gern den grafischen Teil programmieren. Leider fehlt mir da das Wissen. Ich habe folgende KLasse erstellt um ein Viereck zeichnen zu können. Eigentlich soll nach dem Start der Applikation alles auf einem View sein, sowohl Eingabemöglichkleiten und der grafische Teil. Wie kann ich dies erreichen?? Leider sind die Tutorials oft nur für den Einstieg. Die folgende KLasse habe ich implementiert um die gewünschten Grafiken zu erstellen, leider überschreibt diese dann den View und der alte View mit den Buttons ist dann überschrieben?!
    Code:
    package com.jb;
    
    
    import android.content.Context;
    import android.graphics.Canvas;
    import android.view.View;
    import android.graphics.drawable.ShapeDrawable;
    import android.graphics.drawable.shapes.OvalShape;
    
    public class MyDrawableView extends View
    {
        private ShapeDrawable mDrawable;
    
        public MyDrawableView(Context context)
        {
            super(context);
    
            int x = 10;
            int y = 10;
            int width = 300;
            int height = 50;
    
            mDrawable = new ShapeDrawable(new OvalShape());
            mDrawable.getPaint().setColor(0xff74AC23);
            mDrawable.setBounds(x, y, x + width, y + height);
        }
    
        protected void onDraw(Canvas canvas) {
            mDrawable.draw(canvas);
        }
    }
    
    
    Code:
    /** Called when the activity is first created. */
        @Override
        public void onCreate(Bundle savedInstanceState)
        {
            
            super.onCreate(savedInstanceState);
            setContentView(R.layout.main);
            
            
            MyDrawableView mCustomDrawableView;
            mCustomDrawableView = new MyDrawableView(this);
            setContentView(mCustomDrawableView);
    
    wenn ich das neue Objekt lade weis ich nicht wie ich den alten view und den neuen View kombinieren kann.

    Ein Link mit tiefergehenden Tutorial würde mir auch reichen. open gl möchte ich da erstmal außer acht lassen!! wichtig wäre auch wie ich das mit der Bewegung hin bekomme!

    Vielen Dank LG Jim
     
  2. Fr4gg0r, 08.05.2010 #2
    Fr4gg0r

    Fr4gg0r App-Anbieter (Werbung)

    Beiträge:
    2,506
    Erhaltene Danke:
    447
    Registriert seit:
    21.12.2009
    Ich nehme mal an, deine Eingabemöglichkeiten definierst du im xml File.
    Code:
    <LinearLayout id=l1>
    EditText
    EditText
    </LinearLayout>
    Dann kannst du deine "Custom View" hinzufügen, indem die Methode addView von dem LinearLayout aufrufst.
    ((LinearLayout)findViewById(R.id.l1)).addView(mCustomDrawableView);
    Code:
          super.onCreate(savedInstanceState);
            setContentView(R.layout.main);
            MyDrawableView mCustomDrawableView;
            mCustomDrawableView = new MyDrawableView(this);
           ((LinearLayout)findViewById(R.id.l1)).addView(mCustomDrawableView);
    
    Vierecke kannst du einfach mit der Funktion canvas.drawRect(links, oben, rechts, unten); zeichnen, jedoch nur, solange dessen Seiten parallel zu den Bildschirmrändern verlaufen.
    Ansonsten musst du das Viereck in 2 Dreiecke unterteilen.
    Bewegung bekommste, indem du die Koordinaten der Objekte veränderst, damit dass nicht alles in Sekunden Bruchteilen geschieht, kann man Thread.sleep(); benutzen.
     
    Zuletzt bearbeitet: 08.05.2010
  3. jim, 11.05.2010 #3
    jim

    jim Threadstarter Android-Hilfe.de Mitglied

    Beiträge:
    74
    Erhaltene Danke:
    0
    Registriert seit:
    02.05.2010
    Hallo...

    ja ich definiere das Layout in der main.xml und habe dort jetzt folgendes eingefügt
    Code:
    [FONT=Verdana, sans-serif][SIZE=2]<LinearLayout 
       android:id="@+id/layout3"
       android:orientation="horizontal"
       android:layout_width="wrap_content"
       android:layout_height="wrap_content"
      >
                    
                   
       </LinearLayout> [/SIZE][/FONT] 
    
    Ich kann auch jetzt den Kreis sehen, welchen ich hier erstellt habe.
    Code:
    package jb.com;
    
    
    public class MyDrawableView extends View
    {
        private ShapeDrawable mDrawable;
    
        public MyDrawableView(Context context)
        {
            super(context);
    
            int x = 100;
            int y = 100;
            int width = 5;
            int height = 5;
    
            mDrawable = new ShapeDrawable(new OvalShape());
            mDrawable = new ShapeDrawable(new OvalShape());
    
            mDrawable.getPaint().setColor(0xff74AC23);
            mDrawable.setBounds(x, y, x + width, y + height);
            
        }
    
        protected void onDraw(Canvas canvas) {
            mDrawable.draw(canvas);
        }
    }
    Mein erstes Problem wie verschiebe ich die ShapeDrawable?Der Punktoperator hat mir leider keine schlüssige Funktion geben können.. . Eine weitere Sache ist das wenn ich die Werte in der Datei
    int x = 100;
    int y = 100;
    int width = 5;
    int height = 5;
    verändere und auch abspeichere sie nicht verändert auf dem Emulator zu sehen sind(die Veränderungen).

    Oder gehe ich die Sache falsch an?

    @Fr4gg0r -> lustiger bildschirmhintergrund
     
  4. mago, 11.05.2010 #4
    mago

    mago Junior Mitglied

    Beiträge:
    33
    Erhaltene Danke:
    4
    Registriert seit:
    30.04.2010
    Phone:
    HTC Desire
    Mit translate kannst Du den Offset für weitere Zeichenoperationen verändern.

    Code:
    canvas.translate(x, y);
    Dafür müsstest Du dann aber in onDraw() zeichnen. Weil Du ja das einmal im Konstruktor gezeichnetes später nicht mehr verändern kannst.
     
  5. jim, 11.05.2010 #5
    jim

    jim Threadstarter Android-Hilfe.de Mitglied

    Beiträge:
    74
    Erhaltene Danke:
    0
    Registriert seit:
    02.05.2010
    Hallo, ich habe jetzt mal folgenden Code hinzu gefügt.
    1. jetzt werden nicht mehr die Elemente angezeigt (main.xml) sondern nur noch das canvas! ?? -> sprich schwarzer bildschirm und ein kreis welchen ich erzeugt habe
    2. sogar wenn ich den Code ausdokumentiere erscheinen nicht wieder buttons & Co sondern weiterhin der grüne Kreis
    3. die Bewegung, da ich die Werte ja in die hauptActivity besitzte und diese eine velocity bezeichen -> muss ich die Funktion dort aufrufen(HauptActivity ?) mit Parametern?
    4. Wie bekomm ich so eine art mainloop hin?

    Code:
     protected void onDraw(Canvas canvas)
        {    
            //canvas.translate(1,1);
            mDrawable.draw(canvas);
        }
    
    gibt es eigetnlich noch eine gute lektüre ?
    Pragmatic - Hello Android 2nd Edition (2009)
    Android Grundlagen und Programmierung

    diese beiden finde ich zwar hübsch anzuschauen und hilfreich aber das Forum hilft mir da meist weiter..... LG JIm
     
  6. Fr4gg0r, 11.05.2010 #6
    Fr4gg0r

    Fr4gg0r App-Anbieter (Werbung)

    Beiträge:
    2,506
    Erhaltene Danke:
    447
    Registriert seit:
    21.12.2009
    du bekommst eine Loop, indem du (z.b) innerhalb der onDraw invalidate(); aufrufst; denn dieses ruft wieder onDraw auf.
    Zu 1: dafür müssten wir wohl mal dein Code sehen.
    Zu 3: Geht beides. Du kannst sämtliche Methoden deiner View auch über den Punkt Operator aufrufen.

    Allgemein: Warum arbeitest du mit ShapeDrawables? Ich hab keine Ahnung von denen, aber ich nehme an, dass Canvas.irgendwas(); schneller bzw. effektiver ist.

    Wegen der Verschiebung:
    canvas.translate(); wäre eine Möglichkeit, jedoch ist es mMn effizienter direkt die Koordinaten des Objektes zu ändern.
    Es sei denn mehrere Objekte haben genau den gleichen Richtungsvektor.
    Ansonsten musste nämlich wieder mit restore() und nochmal translate arbeiten, sind schonmal mindestens 3 Methodenaufrufe mehr.

    Wegen Verschiebung und Canvas mal ein kurzes Codebeispiel von mir:

    Code:
    private class CustomView extends View {
    private int x1 = 20;
    private int y1 = 20;
    private int x2 = 300;
    private int y2 = 300;
    public void onDraw(Canvas c){
       c.drawCircle(x1, y1, 10); //10 ist der Durchmesser
       c.drawCircle(x2, y2, 10);
      x1 += 2;
      y1 += 5;
      x2 -= 2;
      y2 -= 5;
      try{ Thread.sleep(50); }
      catch(Exception e){ }
      invalidate();
      }
    }
    
    Die erste Kreis wandert hierbei von oben links nach unten rechts, der andere genau entgegengesetzt.
     
  7. jim, 12.05.2010 #7
    jim

    jim Threadstarter Android-Hilfe.de Mitglied

    Beiträge:
    74
    Erhaltene Danke:
    0
    Registriert seit:
    02.05.2010
    Hallo,

    erstmal habe ich gerade folgendes Problem
    ActivityManager: Warning: Activity not started, its current task has been brought to the front

    in einem Forum habe ich folgendes gefunden
    aber das funktioniert nicht.

    Der Kreis lief auch schon von links nach rechts, nun aber nicht mehr.
    Hier also mal der ganze Code
    Code:
    
    public  class gravity_Game extends Activity 
    {
        
        
         private EditText inputValue;
        //private double inputValueAsDouble;
         private int velocity;
        private double velocityDouble;
         /////////////////////////////////////////////////////////////////////////////////////////////
         /** Called when the activity is first created. */
        @Override
         public void onCreate(Bundle savedInstanceState)
        {
            
             super.onCreate(savedInstanceState);
             setContentView(R.layout.main);
            
            
             MyDrawableView  mCustomDrawableView = new      MyDrawableView(this);
                ((LinearLayout)findViewById(R.id.layout3)).addView(mCustomDrawableView);  
            
                 //////////////////////////////////////////////////////////////////////////////////////////////    
         ///spinner
            Spinner s1 =  (Spinner)findViewById(R.id.Planets);
             ArrayAdapter<CharSequence> adapter =
             ArrayAdapter.createFromResource(this,R.array.Planeten,  android.R.layout.simple_spinner_item);
             s1.setAdapter(adapter); 
          /////////////////////////////////////////////////////////////////////////////////////////////
           
            inputValue = (EditText) findViewById(R.id.EditText01);
             
            inputValue.setOnEditorActionListener(new  OnEditorActionListener()
            {
                public boolean  onEditorAction(TextView v, int actionId, KeyEvent event)
                {
                     if (event.getKeyCode() == KeyEvent.KEYCODE_ENTER)
                     {
                        //velocity = getValue and cast to  double
                        velocityDouble =  Double.parseDouble(inputValue.getText().toString());
                         
                        ///Textview for Inputvalue
                         TextView velocityValue =  (TextView)findViewById(R.id.EditTextValue);
                         velocityValue.setText( velocityDouble + "ms");
                    }
                     return false;
                }
            });
    
    }
    
    Code:
    package  jb.com;
    
    import android.content.Context;
    import  android.graphics.Canvas;
    import android.view.View;
    import  android.graphics.drawable.ShapeDrawable;
    import  android.graphics.drawable.shapes.OvalShape;
    
    public class  MyDrawableView extends View
    {
        private ShapeDrawable mDrawable;
         private int x = 10;
        private int y = 10;
        int width = 30;
         int height = 30;
        public MyDrawableView(Context context)
        {
             super(context);
    
           
    
            mDrawable = new  ShapeDrawable(new OvalShape());
             mDrawable.getPaint().setColor(0xff74AC23);
             mDrawable.setBounds(x, y, x + width, y + height);
            
        }
    
         protected void onDraw(Canvas canvas)
        {    
             //canvas.translate(50,10);
             x += 2;
             // y += 5;
    
             
              mDrawable.setBounds(x, y, x + width, y + height);
             
              
              mDrawable.draw(canvas);
               try{ Thread.sleep(50); }
              catch(Exception e){ }
               
              invalidate();
    
        }
    }
    
    Leider passiert es auch, als der punkt noch gewandert ist, das der rest verschwunden ist(also die buttons) und der Kreis ganz oben lief.
    Wie kann ich die werte(Variable) aus der gravity_game.java bekommen?

    Danke für die Hilfe!!!!!
     
  8. jim, 12.05.2010 #8
    jim

    jim Threadstarter Android-Hilfe.de Mitglied

    Beiträge:
    74
    Erhaltene Danke:
    0
    Registriert seit:
    02.05.2010
    also das Problem mit
    "ActivityManager: Warning: Activity not started, its current task has been brought to the front "
    kann doch durch das Verändern (leertaste-> abspeichern)der hauptactivity gelöst werden.
    Mein Problem ist gerade das ich in der folgenden Klasse alles ausdokumentiert habe und er anscheinend irgendwoher die alte nimmt!

    Code:
    package jb.com;
    
    import android.content.Context;
    import android.graphics.Canvas;
    import android.view.View;
    import android.graphics.drawable.ShapeDrawable;
    import android.graphics.drawable.shapes.OvalShape;
    
    public class MyDrawableView extends View
    {
            private ShapeDrawable mDrawable;
    //         int x = 10;
    //         int y = 10;
    //        int width = 10;
    //        int height = 10;
            
        public MyDrawableView(Context context)
        {
            super(context);
        
            
           
            
            
    //        mDrawable = new ShapeDrawable(new OvalShape());
    //        mDrawable.getPaint().setColor(0xFF0000FF);
            
            
        }
        @Override
        protected void onDraw(Canvas canvas)
        {    
    //        canvas.translate(50,10);
    //         x += 2;
    //          y += 5;
            
              mDrawable.draw(canvas);
    //          mDrawable.setBounds(x, y, x + width, y + height);
    //         
    //          invalidate();
              
    //          try{ Thread.sleep(50); }
    //          catch(Exception e){ }
    
    Wie kann das sein???
     
    Zuletzt bearbeitet: 13.05.2010
  9. Fr4gg0r, 13.05.2010 #9
    Fr4gg0r

    Fr4gg0r App-Anbieter (Werbung)

    Beiträge:
    2,506
    Erhaltene Danke:
    447
    Registriert seit:
    21.12.2009
    Das ist überhaupt kein Problem.
    Das ist ledigliche eine "Fehlermeldung", die auftritt, wenn du versuchst dein aktuelles Projekt auf dem Emulator zu installieren, obwohl es keinen Unterschied zu der Version auf dem Emulator gibt.
    Also, nur installieren drücken, wennde was geänder hast.;)
    Zum Starten kannst du ja im App Menü die App im Emulator auswählen...
     
  10. jim

    jim Threadstarter Android-Hilfe.de Mitglied

    Beiträge:
    74
    Erhaltene Danke:
    0
    Registriert seit:
    02.05.2010
    Ich bin mir nicht sicher was du mit installieren meinst. Ich benutze eclipse mit dem emulator. Wie vorher beschrieben benutze ich die "leerzeichen einfügen und löschen und dazwischen abspeichern" Technik. Jetzt habe ich festgestellt das er die Klasse nicht aktulisiert also auf dem emulator (AVD). siehe oben. ich dachte schon ich werde bescheuert!!!
     
  11. Fr4gg0r, 13.05.2010 #11
    Fr4gg0r

    Fr4gg0r App-Anbieter (Werbung)

    Beiträge:
    2,506
    Erhaltene Danke:
    447
    Registriert seit:
    21.12.2009
    Die Frage ist "Für was zu tue"?:D
    Wenn du Run (in Eclipse) auswählst, dann wird die Version auf dem Emulator installiert und die alte überschrieben; gleichzeitig wird die App gestartet.
    Unterscheidet sich nun die auf dem Emulator von der die du gerade installierst nicht, so kommt die o.g. "Fehlermeldung".
    Es ist total unnötig jedes mal eine kleine Änderung zu machen, damit Eclipse nicht meckert, stattdessen einfach im Emulator die App starten.
    Die Ausnahme ist, wenn noch kein Emulator vorhanden ist, dann "darf" man, obwohl man nichts geändert hat, Run auswählen in Eclipse.
    Achja, falls du deine App komplett abschießen und neustarten möchtest (vll. ist das ja dein Anliegen...), so reicht es wenn du den Back-Button drückst.
    Dieser ruft standardmäßig die onDestroy Methode auf, womit die gesamte App tot ist.
    Ich nehme mal an, dies wolltest du wohl erreichen...


    Wegen dem Code:
    edit: ne hab mich verguckt.
     
    Zuletzt bearbeitet: 13.05.2010
  12. jim

    jim Threadstarter Android-Hilfe.de Mitglied

    Beiträge:
    74
    Erhaltene Danke:
    0
    Registriert seit:
    02.05.2010
    Hallo,

    mein Problem war das sich jene Klasse nicht aktualisiert, welche ich in der extends activity benutze.... (und das weil ich ein Idiot bin!!--> habe die falsche Datei editiert..... grrrrrrr)
    soweit klappt jetzt alles. Jetzt brauch ich den Wert aus dem Edittext und dachte ich könnte das so machen.
    Da ich den Wert in der extends View
    Code:
    public class MyDrawableView extends View
    {
    
            private ShapeDrawable mDrawable;
            ///Textview for Inputvalue
            TextView velocityValue;
            Drawable myImage;
            int x = 0;
            int y = 0;
            int width = 100;
            int height = 100;
            int speed =0;
            EditText inputValue = (EditText)findViewById(R.id.EditText01);
           
           
           
        
           
        public MyDrawableView(Context context)
        {
            super(context );
           
        
           
            inputValue.setOnEditorActionListener(new OnEditorActionListener()
            {
                public boolean onEditorAction(TextView v, int actionId, KeyEvent event)
                {
                    if (event.getKeyCode() == KeyEvent.KEYCODE_ENTER)
                    {
                        //speed = getValue and cast to double
                        speed = Integer.parseInt(inputValue.getText().toString());
                       
                        ///Textview for Inputvalue
                        TextView velocityValue = (TextView)findViewById(R.id.EditTextValue);
                        velocityValue.setText( speed + "ms");
                    }
                    return false;
                }
            }
            );
            ///load picture
            Resources res = context.getResources();
             myImage = res.getDrawable(R.drawable.cabrio);
             myImage.setBounds(x, y, x + width, y + height);
           
       
           
           
           
            mDrawable = new ShapeDrawable(new OvalShape());
            mDrawable.setBounds(x, y, x + width, y + height);
            mDrawable.getPaint().setColor(0xFF0000FF);
           
           
        }
        @Override
        public void onDraw(Canvas canvas)
        {   
           
            //canvas.translate(90,10);
             
              //y += 1;
           
            x += speed;
           
           if(x>=100 || x < 0)
                speed *= -1;
           
           
           
               
            myImage.draw(canvas);
              //mDrawable.draw(canvas);
             
              myImage.setBounds(x, y, x + width, y + height);
    //         
              invalidate();
             
    //          try{ Thread.sleep(50); }
    //          catch(Exception e){ }
    
        }
    }
    
    nachdem ich den Teil mit dem Listener ausdokumentiert habe funktioniert es wieder. Gibt es einen anderen Weg den Wert zu bekommen? bzw. warum funktioniert das so nicht. vielen vielen dank!
     
    Zuletzt bearbeitet: 14.05.2010

Diese Seite empfehlen