Layout und Canvas zusamen einsetzen

  • Antworten:16
Gelöschter Account
  • Forum-Beiträge: 10

19.10.2011, 21:49:56 via Website

Hallo Leute,

schreibe heute zum ersten mal hier und arbeite schon eine Weile mit meinem Tutorial hier mich in die Android Oberfläche ein.
Ich bin gerade an einen Punkt gekommen wo ich ein normales Layout mit peronalisierten Buttons zusammen mit einem Canvas einsetzen muss.
Ich habe dazu auch sehr viel im Internet gefunden, doch irgendwie klappt das bei mir so nicht.

Programmieren tu ich für ein TF101 Honeycomb Tablet. Android 3.2.1

Hoffe jemand kann mir helfen.
Dennis

Antworten
Ansgar M
  • Forum-Beiträge: 1.544

19.10.2011, 21:55:48 via Website

Das sollte eigentlich klappen, die Dinge zu vermischen :)
Wo genau liegt denn dein Problem? Was klappt nicht?
Lg Ansgar

Antworten
Gelöschter Account
  • Forum-Beiträge: 10

19.10.2011, 22:05:29 via Website

Ich hab hier mal ein Beispiel aus dem Internet implementiert. Leider stürtt die Anwendung beim Start sofort wieder ab.
Ich hab es auch schon etwas ähnlich hinbekommen, dass nur der Canvas da war, doch das ist nciht ganz richtig gewesen.
Ich hab den Ablauf hier einfach noch nicht geschnallt?
Wie hättet Ihr das gemacht?

1package de.robotcontrol.debegr;
2
3import android.app.Activity;
4import android.content.Context;
5import android.graphics.Bitmap;
6import android.graphics.BitmapFactory;
7import android.graphics.Canvas;
8import android.graphics.Typeface;
9import android.os.Bundle;
10import android.view.MotionEvent;
11import android.view.SurfaceHolder;
12import android.view.SurfaceView;
13import android.view.View;
14import android.view.View.OnClickListener;
15import android.view.View.OnTouchListener;
16import android.view.Window;
17import android.view.WindowManager;
18import android.view.WindowManager.LayoutParams;
19import android.widget.Button;
20import android.widget.FrameLayout;
21import android.widget.LinearLayout;
22import android.widget.SlidingDrawer;
23import android.widget.TextView;
24
25public class Playground extends Activity implements OnTouchListener, OnClickListener{
26
27 PlaygroundSurface ourSurfaceView;
28 Typeface sevenSegFont;
29 TextView tvSlidingDrawer;
30 Button bGrenade,bSmokeGrenade;
31 SlidingDrawer sdHandle;
32 TextView tvX,tvY;
33 Bitmap bitmapJoyGround,bitmapJoyButton;
34 float curX,curY;
35 String sBuffer;
36 FrameLayout layout;
37
38
39 @Override
40 protected void onCreate(Bundle savedInstanceState) {
41 // TODO Auto-generated method stub
42 super.onCreate(savedInstanceState);
43 //requestWindowFeature(Window.FEATURE_NO_TITLE);
44 //setContentView(R.layout.playground);
45
46 this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,WindowManager.LayoutParams.FLAG_FULLSCREEN);
47
48
49 ourSurfaceView = new PlaygroundSurface(this);
50 ourSurfaceView.setOnTouchListener(this);
51
52 layout = (FrameLayout) findViewById(R.id.lFrameLayout);
53 ourSurfaceView = new PlaygroundSurface(this);
54 layout.addView(ourSurfaceView);
55 setContentView(layout);
56
57 curX = curY = 0;
58
59 // Handle for the TExt in the SlidingDrawer
60 tvSlidingDrawer = (TextView) findViewById(R.id.sdHandle);
61
62 // TextViews
63 tvX = (TextView) findViewById(R.id.tvX);
64 tvY = (TextView) findViewById(R.id.tvY);
65
66 // Creates the 7-Segment font handle
67 sevenSegFont = Typeface.createFromAsset(this.getAssets(), "7 Segment.ttf");
68 //tvSlidingDrawer.setText("12:00");
69
70 // Handle for the Bitmaps
71 bitmapJoyButton = BitmapFactory.decodeResource(getResources(), R.drawable.joy_button);
72 bitmapJoyGround = BitmapFactory.decodeResource(getResources(), R.drawable.joy_ground);
73 }
74
75
76
77 @Override
78 protected void onPause() {
79 // TODO Auto-generated method stub
80 super.onPause();
81 ourSurfaceView.pause();
82 }
83
84
85 @Override
86 protected void onResume() {
87 // TODO Auto-generated method stub
88 super.onResume();
89 ourSurfaceView.resume();
90 }
91
92
93 @Override
94 public boolean onTouch(View arg0, MotionEvent arg1) {
95 // TODO Auto-generated method stub
96
97 try {
98 Thread.sleep(50);
99 } catch (InterruptedException e) {
100 // TODO Auto-generated catch block
101 e.printStackTrace();
102 }
103
104 try {
105 Thread.sleep(50);
106 } catch (InterruptedException e) {
107 // TODO Auto-generated catch block
108 e.printStackTrace();
109 }
110
111 curX = arg0.getX();
112 curY = arg0.getY();
113
114 tvX.setText(""+curX);
115 tvY.setText(""+curY);
116
117 return true;
118 }
119
120 @Override
121 public void onClick(View arg0) {
122 // TODO Auto-generated method stub
123
124 }
125
126
127 public class PlaygroundSurface extends SurfaceView implements Runnable {
128
129 SurfaceHolder surfaceHolder;
130 boolean isRunning = true;
131 Thread ourThread = null;
132
133
134 public PlaygroundSurface(Context context) {
135 super(context);
136 surfaceHolder = getHolder();
137 }
138
139 public void pause(){
140 isRunning = false;
141 while(true){
142 try {
143 ourThread.join();
144 } catch (InterruptedException e) {
145 // TODO Auto-generated catch block
146 e.printStackTrace();
147 }
148 break;
149 }
150 ourThread = null;
151 }
152
153 public void resume(){
154 isRunning = true;
155 ourThread = new Thread(this);
156 ourThread.start();
157 }
158
159 @Override
160 public void run() {
161 // TODO Auto-generated method stub
162 while(isRunning){
163 if(!surfaceHolder.getSurface().isValid())
164 continue;
165
166 Canvas canvas = surfaceHolder.lockCanvas();
167
168 canvas.drawBitmap(bitmapJoyGround, 0, 450, null);
169 canvas.drawBitmap(bitmapJoyGround, 700, 450, null);
170
171 surfaceHolder.unlockCanvasAndPost(canvas);
172 }
173 }
174 }
175
176}

Antworten
Gelöschter Account
  • Forum-Beiträge: 10

20.10.2011, 12:07:25 via Website

Hey,
Hat das jetzt schonmal jemand gemacht oder nicht?
Wäre wirklich sehr verbunen, wenn mir das jemand an meinem code erklärt, denn mein tutorial geht darauf leider nicht ein.

Danke schonmal.
Dennis

Antworten
Ansgar M
  • Forum-Beiträge: 1.544

20.10.2011, 12:24:52 via App

Hey,
wenn du sagst, dass es abstürzt, was ist da die Meldung im Logcat?
Lg Ansgar

Antworten
Gelöschter Account
  • Forum-Beiträge: 10

20.10.2011, 13:02:21 via Website

Hier die Meldung bei INFO:

10-20 13:05:10.230: INFO/dalvikvm-heap(2316): Grow heap (frag case) to 7.890MB for 327696-byte allocation
10-20 13:05:10.280: INFO/dalvikvm-heap(2316): Grow heap (frag case) to 8.200MB for 327696-byte allocation
10-20 13:05:10.320: INFO/dalvikvm-heap(2316): Grow heap (frag case) to 8.512MB for 327696-byte allocation
10-20 13:05:11.450: INFO/ActivityManager(134): Starting: Intent { cmp=de.robotcontrol.debegr/.Playground } from pid 2316
10-20 13:05:17.780: INFO/Email(2178): ReconcilePopImapAccountsSync: start
10-20 13:05:17.800: WARN/Email(2178): Received BYE
10-20 13:05:17.800: INFO/Email(2178): ReconcilePopImapAccountsSync: done
10-20 13:05:19.810: INFO/Email(2178): ReconcilePopImapAccountsSync: start
10-20 13:05:19.830: WARN/Email(2178): Received BYE
10-20 13:05:19.840: INFO/Email(2178): ReconcilePopImapAccountsSync: done
10-20 13:05:21.530: WARN/ActivityManager(134): Launch timeout has expired, giving up wake lock!
10-20 13:05:21.530: WARN/ActivityManager(134): Activity idle timeout for ActivityRecord{414d09d0 de.robotcontrol.debegr/.Playground}

Kann mir daraus aber nicht wirklich viel herleiten...
Stimmt denn überhaupt mein Ansatz oben, das FrameLayout zu speichern und diesem einfach das andere anzuhängen? Und dann das gesamte zu öffnen?

Antworten
Maximilian O
  • Forum-Beiträge: 990

20.10.2011, 13:07:09 via App

Hey, ist das wirklich das was logcat unter ddms ausgibt? Sieht bissl wenig aus. Trotzdem stehen doch in dem was Du gepostet hast, wenn das zu deinem app gehört genug Infos, schau dir dochmal die letzten beiden Zeilen an.
MfG

Vergiss nie wieder Geburtstage, oder viel schlimmer, deinen Hochzeitstag - Birthdays Download

Antworten
Gelöschter Account
  • Forum-Beiträge: 10

20.10.2011, 13:23:49 via Website

Maximilian O
Hey, ist das wirklich das was logcat unter ddms ausgibt? Sieht bissl wenig aus. Trotzdem stehen doch in dem was Du gepostet hast, wenn das zu deinem app gehört genug Infos, schau dir dochmal die letzten beiden Zeilen an.
MfG

Ja okay, ich hab die Warnungen schon gesehn, doch was sagen Sie aus? Wonach muss ich suchen?
Ich kann per setContentView den Screen auf die Klasse oder auf mein FrameLayout richten, aber nicht auf beides zusammen, das heißt bei der Funktion addView sollte irgend etwas falsch laufen oder?
Wie macht man das normal? Welche Funktionen benutzt man?
Woher soll man den sowas bekommen?

Antworten
Maximilian O
  • Forum-Beiträge: 990

20.10.2011, 15:49:18 via App

Naja, versuche doch einmal deine xml als contentview zu setzen. Darin definierst du von mir aus ein relativ layout, welchen du dann dein canvas addest.
mfg

Vergiss nie wieder Geburtstage, oder viel schlimmer, deinen Hochzeitstag - Birthdays Download

Antworten
Gelöschter Account
  • Forum-Beiträge: 10

20.10.2011, 20:44:51 via Website

Maximilian O
Naja, versuche doch einmal deine xml als contentview zu setzen. Darin definierst du von mir aus ein relativ layout, welchen du dann dein canvas addest.
mfg

Okay, also Layout erstellt, ID an das FrameLayout vergeben. Canvas erstellt. Welcher Befehl schiebt nun das Layout in das Canvas? So meintest du es doch oder?
Aber mal anderst gefragt, wenn einfach ein kleines Beispiel kam, wär das sehr viel hilfreicher, aber wenn man das noch nie gemacht hat ist das verdammt schwer -.-

Aber danke schonmal.

Antworten
Maximilian O
  • Forum-Beiträge: 990

20.10.2011, 22:14:02 via App

Schicke dir morgen mal ein Beispiel. Bin derzeit noch im Urlaub, deshalb konnte ich keinen Code Posten. Aber egal. Also bis morgen.
MfG

Vergiss nie wieder Geburtstage, oder viel schlimmer, deinen Hochzeitstag - Birthdays Download

Antworten
Gelöschter Account
  • Forum-Beiträge: 10

21.10.2011, 06:45:44 via Website

Hey danke!
Bin ich ja mal gespannt!

Dennis

Antworten
Maximilian O
  • Forum-Beiträge: 990

21.10.2011, 20:55:33 via Website

Hey,
also ich mache das folgendermaßen:
1setContentView(R.layout.level3);
2
3 gameLayout = (RelativeLayout) findViewById(R.id.playingField);
4
5 MyDraw mydraw = new MyDraw(this); //das ist die Klasse die die Surfaceview extendet
6 gameLayout.addView(mydraw);

MfG

Vergiss nie wieder Geburtstage, oder viel schlimmer, deinen Hochzeitstag - Birthdays Download

Antworten
Gelöschter Account
  • Forum-Beiträge: 10

21.10.2011, 21:05:11 via Website

Hey,

Also ich werde es morgen mal ausprobieren, danke!

Antworten
Gelöschter Account
  • Forum-Beiträge: 10

21.10.2011, 22:25:16 via Website

Hey,
habs doch heut noch geschafft. Der Code funktioniert jetzt erstmal grundlegend, bzw stürtzt eben halt nicht mehr ab. Nun habe ich bei meinem Layout, welches DIREKT IM SPIEL angezeigt werden soll, das erste Layout als FrameLayout definiert. Hab diesem eine ID zugewießen. Aber das ist ja die selbe XML wie ich am Anfang auf setContentView gesetzt habe. Ist das richtig?
Was mir nun noch helfen würde wär, wenn du mir deine grundlegende SurfaceView Klasse zeigst. Ich bin mir nicht sicher, ob bei mir alles stimmt.

Aber danke schonmal! Warst mir bis jetzt eine verdammt große Hilfe!

Antworten
Maximilian O
  • Forum-Beiträge: 990

22.10.2011, 15:50:38 via Website

Hey,
also meine "Canvas" Klasse sieht in etwa so aus:
1package com.XYZ;
2
3public class MyDraw extends SurfaceView implements Callback {
4
5 private MainThread mainThread;
6
7 private SurfaceHolder holder;
8
9 @SuppressWarnings("unchecked")
10 public MyDraw(Activity activity)
11 {
12 super(activity.getApplication());
13 this.activity = activity;
14
15 holder = getHolder();
16 holder.addCallback(this);
17
18 //lade hier alle Bitmaps die du benötigst
19
20
21 }
22
23 public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
24
25 }
26
27 public void surfaceCreated(SurfaceHolder holder) {
28 mainThread = new MainThread(holder, this, activity);
29 mainThread.setRunning(true);
30 mainThread.start();
31 }
32
33 public void surfaceDestroyed(SurfaceHolder holder) {
34
35 }
36
37 @Override
38 public boolean onTouchEvent(MotionEvent event) {
39
40 return true;
41 }
42
43 @Override
44 protected void onDraw(Canvas canvas) {
45 super.onDraw(canvas);
46 //repaint dein canvas
47 }
48
49
50}

MfG

//achso, ich habe den MainThread mit dem MainLoop in einer extra Klasse.

— geändert am 23.10.2011, 13:14:47

Vergiss nie wieder Geburtstage, oder viel schlimmer, deinen Hochzeitstag - Birthdays Download

Antworten
Gelöschter Account
  • Forum-Beiträge: 10

23.10.2011, 12:22:57 via Website

Hey, danke für deinen Code! Hab ihn nun mal bei mir implementiert.
Jetzt legt er einen Contructor für meine Normale Klasse an, zu welcher ich den SurfaceView haben will.

1public Playground(SurfaceHolder holder,
2 PlaygroundSurface playgroundSurface, Activity activity) {
3 // TODO Auto-generated constructor stub
4 }

Wie sieht diese Funktion bei dir aus? Die Applikation schmiert bei mir dort immer ab. Und die Fehlermeldung aus dem Catlog ist immer die selbe. Nämlich die die oben steht. Einen eindeutigen Fehler kann man hieraus ja nicht ableiten, oder geht das doch? Also das das Catlog mit zum Beispiel sagt, diese Funktion ruft einen Error hervor.

Weiß da jemand Rat?

Grüße
Dennis

Antworten