I am trying to use Canvas that has been created in external class.
However, the app does not run. Here is my code for MyImge where activity starts
import android.app.Activity;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Bundle;
import android.widget.ImageView;
public class MyImage2 extends Activity {
DemoView draw;
private int imageSizeX = 2047;
private int imageSizeY = 2047;
private int current_drawable = R.drawable.image;
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
Map<String, Integer> map = new HashMap<String, Integer>();
map.put("blah", current_drawable);
ImageView img=(ImageView)findViewById(R.id.imageView);
Bitmap bmp=BitmapFactory.decodeResource(getResources() ,current_drawable);
draw = (DemoView)findViewById(R.id.demo);
imageSizeX = bmp.getWidth()/2;
imageSizeY = bmp.getHeight()/2;
Bitmap resizedbitmap=Bitmap.createScaledBitmap(bmp, imageSizeX, imageSizeY, true);
img.setImageBitmap(resizedbitmap);
}
}
and my DemoView as follows
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.view.View;
public class DemoView extends View{
public DemoView(Context context){
super(context);
}
#Override protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
Paint paint = new Paint();
paint.setStyle(Paint.Style.FILL);
// make the entire canvas white
paint.setColor(Color.WHITE);
canvas.drawPaint(paint);
paint.setAntiAlias(false);
paint.setColor(Color.GREEN);
canvas.drawRect(100, 5, 200, 30, paint);
canvas.drawLine(0, 300 , 320, 300, paint);
}
}
the layout
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
>
<ImageView
android:id="#+id/imageView"
android:layout_width="fill_parent"
android:scaleType="matrix"
android:layout_height="525px">
</ImageView>
<view class="com.test.DemoView"
android:id="#+id/demo"
android:layout_width="fill_parent"
android:layout_height="125px"/>
</LinearLayout>
if I remove the tag com.myimage2.DemoView I can see the image, however my goal is to see the image and canvas. Could someone help please.
Error log:
!ENTRY com.android.ide.eclipse.adt 2 0 2011-04-10 02:19:27.204
!MESSAGE AndroidManifest: Ignoring unknown 'com.test.DemoView' XML element
!ENTRY com.android.ide.eclipse.adt 2 0 2011-04-10 02:19:27.891
!MESSAGE AndroidManifest: Ignoring unknown 'view' XML element
Many thanks in advance.
I think you need to provide one of the other constructors (one that can handle AttributeSet) in order for the classs to be instantiated from xml. Try adding DemoView(Context context, AttributeSet attrs).
I don't know what you want to do with your code in your onCreate-method in the class "MyImage2".
You need just 2 lines to set a canvas view:
draw=new DemoView(this);
setContentView(draw);
By setting your content view to the main layout, the canvas will never be seen. So don't use your main layout, just print everything in the canvas.
Hope this will help you.
Related
I want to show a list of three separate textviews in my linear layout. I'm aware that this can be done from the XML file itself , but I want to generate these textviews dynamically.
XML file:
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
xmlns:card_view="http://schemas.android.com/apk/res-auto"
android:layout_height="fill_parent"
android:layout_width="fill_parent"
android:id = "#+id/ll1">
</LinearLayout>
Java file:
import android.content.Intent;
import android.os.Bundle;
import android.view.LayoutInflater;
import android.view.TextureView;
import android.view.View;
import android.view.ViewGroup;
import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.appcompat.app.AppCompatActivity;
import androidx.fragment.app.Fragment;
import androidx.navigation.fragment.NavHostFragment;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
public class RegistrationActivity extends AppCompatActivity {
#Override
protected void onCreate(Bundle saved){
LinearLayout ll = findViewById(R.id.ll1);
super.onCreate(saved);
setContentView(R.layout.activity_reg);
List<String> names = new ArrayList<>(Arrays.asList("Negotiation","Pyschology","Joke"));
for (int i = 0; i<3;++i){
TextView dynamic = new TextView(this);
dynamic.setText(names.get(i));
dynamic.setTextSize(14);
dynamic.setOnClickListener(new View.OnClickListener() {
#Override
public void onClick(View view) {
startActivity(new Intent(RegistrationActivity.this, MainActivity.class));
}
});
ll.addView(dynamic);
}
}
}
The result is a blank page and what I want is three clickable textviews as the result. Where did I go wrong?
If I am not wrong sir you want to add Text view Programmatically
Find you need a layout parent layout Your parent layout is Linear layout set id of a linear layout Suppose id is linerlayout_parent After this in Activity
LinearLayout linearview = findViewById(R.id.linerlayout_parent);
Now Here Create text view Programatically
TextView title=new TextView(Activity.this);
title.setTextSize(20);
title.setTextAppearance(context,R.font.abhaya_libre_bold);
title.setPadding(10,10,10,10);
title.setTextColor(Color.BLACK);
title.setText("Hello use this code");
linearview.addView(title);
if you need three than in Loop paste this code
Kindly set orientation of a Linear layout Vertical
May be you forgot to add textview in parentview like this.
tv[i] = new TextView(this);
RelativeLayout.LayoutParams params=new RelativeLayout.LayoutParams
((int)LayoutParams.WRAP_CONTENT,(int)LayoutParams.WRAP_CONTENT);
params.leftMargin = 50;
params.topMargin = i*50;
tv[i].setText(str[i]);
tv[i].setTextSize((float) 20);
tv[i].setPadding(20, 50, 20, 50);
tv[i].setLayoutParams(params);
rl.addView(tv[i]);
Can someone point me in the direction of how to trigger an animation when using databinding?
I've got an icon which changes according to data in my viewmodel. How do I animate icon change when the viewmodel changes (that is, when a property changes in the viewmodel)?
One possible solution is to use a binding adapter.
Here's a quick sample to show you the way to go:
First we define a custom binding adapter:
import android.databinding.BindingAdapter;
import android.support.v4.view.animation.FastOutSlowInInterpolator;
import android.view.View;
import android.view.animation.Animation;
import android.view.animation.Interpolator;
import android.view.animation.RotateAnimation;
import android.view.animation.TranslateAnimation;
public class ViewBusyBindings {
private static final Interpolator INTERPOLATOR = new FastOutSlowInInterpolator();
#BindingAdapter("isBusy")
public static void setIsBusy(View view, boolean isBusy) {
Animation animation = view.getAnimation();
if (isBusy && animation == null) {
view.startAnimation(createAnimation());
} else if (animation != null) {
animation.cancel();
view.setAnimation(null);
}
}
private static Animation createAnimation() {
RotateAnimation anim = new RotateAnimation(0, 360, Animation.RELATIVE_TO_SELF, 0.5f, Animation.RELATIVE_TO_SELF, 0.5f);
anim.setInterpolator(INTERPOLATOR);
anim.setDuration(1400);
anim.setRepeatCount(TranslateAnimation.INFINITE);
anim.setRepeatMode(TranslateAnimation.RESTART);
return anim;
}
}
The example layout will look like this:
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto">
<data>
<variable
name="vm"
type="de.example.exampleviewmodel"/>
</data>
<FrameLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
>
<ImageButton
android:id="#+id/btnPlay"
style="?attr/borderlessButtonStyle"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="right|bottom"
android:src="#drawable/ic_play_circle_filled_white_36dp"
app:isBusy="#{vm.isBusy}"/>
</FrameLayout>
</layout>
As you can see, the 'isBusy' property of your viemodel is bound to the view (imagebutton).
You can use this adapter at any view not only at a imagebutton.
Of course, the 'isBusy' property must be bindable (e.g. your viewmodel extends BaseObservable or as a minimum it's a ObservableBoolean).
So whenever you change the 'isBusy' property to true it will trigger the animation to start.
Set it to false, it stops.
Hope this helps ?
I'm trying to create a rectangle within a canvas so that it appears on the right hand side of the screen but the app seems to crash every time I run it. I seriously don't know am I doing wrong here + what needs to change within my code?
activity_main.xml
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:orientation="vertical"
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:paddingLeft="#dimen/activity_horizontal_margin"
android:paddingRight="#dimen/activity_horizontal_margin"
android:paddingTop="#dimen/activity_vertical_margin"
android:paddingBottom="#dimen/activity_vertical_margin"
tools:context=".MainActivity">
<TextView android:text="#string/hello_world" android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<com.apptacularapps.customview.DrawView
android:id="#+id/diagram"
android:layout_width="fill_parent"
android:layout_height="52dp" />
</LinearLayout>
MainActivity.java
import android.graphics.Color;
import android.os.Bundle;
import android.support.v7.app.ActionBarActivity;
import android.view.Menu;
import android.view.MenuItem;
public class MainActivity extends ActionBarActivity {
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
DrawView drawView = new DrawView(this);
drawView.setBackgroundColor(Color.BLACK);
setContentView(drawView);
}
}
DrawView.java
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Point;
import android.view.Display;
import android.view.View;
import android.view.WindowManager;
public class DrawView extends View {
Paint paint = new Paint();
Context context;
public DrawView(Context context) {
super(context);
this.context = context;
}
#Override
public void onDraw(Canvas canvas) {
//Code to Measure the Screen width in pixels
WindowManager wm = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
Display display = wm.getDefaultDisplay();
Point size = new Point();
display.getSize(size);
int width = size.x;
paint.setColor(Color.RED);
canvas.drawRect(0, 0, 5, canvas.getHeight(), paint );
paint.setColor(Color.RED);
canvas.drawRect(canvas.getWidth()-width, 0, 5, canvas.getHeight(), paint );
}
}
My earlier answer was because of my lack of understanding of your problem. Sorry for the inconvenience caused, if any. I am not sure if i can help you, but try this.
public void onDraw(Canvas canvas) {
//Code to Measure the Screen width in pixels
WindowManager wm = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
Display display = wm.getDefaultDisplay();
Point size = new Point();
display.getSize(size);
int width = size.x;
paint.setColor(Color.RED);
canvas.drawRect(0, 0, 5, canvas.getHeight(), paint );
paint.setColor(Color.RED);
canvas.drawRect(canvas.getWidth()-width, 0, 5, canvas.getHeight(), paint );
}
In the above piece of code, in the last line, instead of canvas.getWidth()-width, type canvas.getWidth()-(float) width. Because width is integer and canvas.getWidth() returns float and float-int returns a recurring floating number.
Check the value of width. Is it as expected ? Also try setting the value width manually and see if the problem persists.
Hope this helps and solves the trouble !
Have a look at this question and its accepted answer.
try this..
<com.example.mystackoverflow.MyView
android:id="#+id/myview"
android:layout_width="match_parent"
android:layout_height="100dp"
android:layout_alignParentTop="true" />
MyView class
public class MyView extends View {
private Paint mPaint;
private int view_width, view_height;
public MyView(Context context, AttributeSet attrs) {
super(context, attrs);
mPaint = new Paint();
mPaint.setColor(getResources().getColor(color.Red));
mPaint.setFlags(Paint.ANTI_ALIAS_FLAG);
}
#Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
//canvas.drawRect(0, 0, view_width, view_height, mPaint);
canvas.drawRect(view_width/2, 0, view_width, view_height, mPaint);
}
#Override
protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
super.onLayout(changed, left, top, right, bottom);
view_width = right - left;
view_height = bottom - top;
}
}
I am trying to create an app that displays a circle everytime I click a button. I have the layout looking great but when i click the button(circle) to display a circle on the screen nothing happens. I'm not confident that my draw circle class is being called correctly in my main activity. Here is my code below.
package com.example.randomcircles;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.graphics.Canvas;
import android.graphics.Paint;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.FrameLayout;
public class DisplayRandomCircles extends Activity
{
DrawCircle c;
Canvas d;
#Override
public void onCreate(Bundle b)
{
super.onCreate(b);
setContentView(R.layout.activity_display_random_circles);
Button btn1 = (Button) findViewById(R.id.btn1);
Button btn2 = (Button) findViewById(R.id.btn2);
c = new DrawCircle(getApplicationContext());
d = new Canvas();
FrameLayout f1 = (FrameLayout) findViewById(R.id.frame);
}
#SuppressLint("WrongCall")
public void doit(View v)
{
switch (v.getId())
{
case (R.id.btn1):
c.onDraw(d);
break;
case (R.id.btn2):
break;
}
}
}
Here is my DrawCircle class
package com.example.randomcircles;
import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.view.View;
public class DrawCircle extends View
{
public DrawCircle(Context con)
{
super(con);
}
#Override
protected void onDraw(Canvas c)
{
super.onDraw(c);
Paint p = new Paint(Paint.ANTI_ALIAS_FLAG);
p.setAntiAlias(true);
p.setStyle(Paint.Style.STROKE);
p.setStrokeWidth(100);
p.setColor(Color.RED);
p.setStyle(Paint.Style.FILL);
c.drawCircle(75, 75, 100, p);
}
}
And my layout xml
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<FrameLayout
android:id="#+id/frame"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:layout_weight=".75"
android:orientation="vertical" >
</FrameLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_weight=".25"
android:gravity="bottom|center"
android:orientation="horizontal" >
<Button
android:id="#+id/btn1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="start|bottom"
android:layout_weight=".50"
android:onClick="doit"
android:text="#string/Circle" />
<Button
android:id="#+id/btn2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_weight=".50"
android:layout_gravity="end|bottom"
android:onClick="doit"
android:text="#string/Clear" />
</LinearLayout>
</LinearLayout>
Ok, here are some changes I'd make for this. I'm not exactly sure what you're trying to do, but this should make things easier.
First, change your class "DrawCircle" like this:
public class DrawCircle extends View
{
final Paint circlePaint;
{
circlePaint = new Paint(Paint.ANTI_ALIAS_FLAG);
circlePaint.setAntiAlias(true);
circlePaint.setStyle(Paint.Style.STROKE);
circlePaint.setStrokeWidth(100);
circlePaint.setColor(Color.RED);
circlePaint.setStyle(Paint.Style.FILL);
}
public DrawCircle(Context con)
{
super(con);
}
public DrawCircle(Context con, AttributeSet set)
{
super(con, set);
}
public DrawCircle(Context con, AttributeSet set, int style)
{
super(con, set, style);
}
#Override
protected void onDraw(Canvas c)
{
super.onDraw(c);
c.drawCircle(75, 75, 100, circlePaint);
}
}
This will allow you to reuse the same Paint object with each draw because the onDraw() method can be called hundreds of times and there's no need to slow down your program for this.
Second, adding the other constructors allows you to add the View to your FrameLayouts by xml.
<FrameLayout
android:id="#+id/frame"
android:layout_width="match_parent"
android:layout_height="match_parent" >
<com.example.randomCircles.DrawCircle
android:id="#+id/circleFrame"
android:layout_width="match_parent"
android:layout_height="match_parent" />
</FrameLayout>
Next, to fill your screen, you need to loop in your onDraw method. Think about drawing on the canvas as a stamp. Every time you draw, you stamp your image at the location you specify on top of the previous draw.
So
protected void onDraw(Canvas c)
{
super.onDraw(c);
for(int i = 0; i < 10; i++)
{
c.drawCircle(i*100, 75, 100, circlePaint);
}
}
This should draw 10 circles of radius 100 pixels across the top of your screen.
I'm working on a simple project for my studies and I’m stuck with this problem.
I'm building Snakes And Ladders app and I’m trying to make my player (PNG image) to move around the board an animate.
I want the animation to happen over the game’s board background which I defined in an xml file and I just can’t do it.
The program that I will attach is not working, I have no idea why. In addition I need to add the part that takes the xml background in consideration, that part is missing and I will greatly appreciate if someone can help me solve this problem.
Thanks in advanced.
The board xml file(game.xml):
<?xml version="1.0" encoding="utf-8"?>
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="#drawable/easymap"
android:orientation="vertical" >
<TextView
android:id="#+id/whitePlayer"
android:layout_width="32dp"
android:layout_height="32dp"
android:background="#drawable/white"
android:visibility="gone" />
<TextView
android:id="#+id/blackPlayer"
android:layout_width="32dp"
android:layout_height="32dp"
android:background="#drawable/black"
android:visibility="gone" />
<Button
android:id="#+id/btRoll"
android:layout_width="160dp"
android:layout_height="50dp"
android:layout_alignParentLeft="true"
android:layout_alignTop="#+id/cubePic"
android:background="#drawable/buttonshape"
android:text="Roll"
android:textColor="#FFFFFF" />
<TextView
android:id="#+id/cubePic"
android:layout_width="100dp"
android:layout_height="100dp"
android:layout_alignParentBottom="true"
android:layout_alignParentRight="true"
android:layout_marginBottom="42dp"
android:layout_marginRight="22dp"
android:background="#drawable/cube" />
<TextView
android:id="#+id/tvTurn"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignBottom="#+id/cubePic"
android:layout_alignRight="#+id/btRoll"
android:text="Your turn!"
android:textColor="#color/green"
android:textSize="32dp"
android:textStyle="italic" />
</RelativeLayout>
The java class:
package com.example.snakesnladders;
import android.app.Activity;
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.os.Bundle;
import android.util.Log;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.TextView;
public class GFX_Game extends Activity implements OnClickListener {
TextView whitePlayer, blackPlayer;
Button roll;
TextView cube, map1, map2, map3, label;
boolean yourTurn = true;
MyBringBack ourView;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
ourView = new MyBringBack(this);
setContentView(ourView);
init();
}
private void init() {
cube = (TextView) findViewById(R.id.cubePic);
roll = (Button) findViewById(R.id.btRoll);
label = (TextView) findViewById(R.id.tvTurn);
roll.setOnClickListener(this);
}
#Override
protected void onDestroy() {
super.onDestroy();
}
#Override
public void onClick(View view) {
int rand = (int) (Math.random() * 6) + 1;
}
class MyBringBack extends SurfaceView implements Runnable {
SurfaceHolder ourHolder;
Thread ourThread = null;
Bitmap backGround, playerB, playerW;
boolean isRunning = true;
public MyBringBack(Context context) {
super(context);
playerW = BitmapFactory.decodeResource(getResources(),
R.id.whitePlayer);
ourHolder = getHolder();
ourThread = new Thread(this);
ourThread.start();
}
#Override
public void run() {
while (isRunning) {
if (!ourHolder.getSurface().isValid())
continue;
Canvas canvas = ourHolder.lockCanvas();
canvas.drawBitmap(playerW, 0, 0, null);
ourHolder.unlockCanvasAndPost(canvas);
}
}
}
}
The changed inner class:( I've extended View an override the onDraw method from the Viev class, and it still not working)
In addition I wanted to draw on my existing xml layout that i created in the game.xml file.
class MyBringBack extends View {
Bitmap playerW;
public MyBringBack(Context context) {
super(context);
playerW = BitmapFactory.decodeResource(getResources(),
R.id.whitePlayer);
}
#Override
protected void onDraw(Canvas canvas) {
// TODO Auto-generated method stub
super.onDraw(canvas);
canvas.drawBitmap(playerW,0,0,null);
}
}
Create a custom View as follows. If you're root view is RelativeLayout and you need to draw on it, extend a RelativeLayout
public final class MyRelativeLayout extends RelativeLayout {
Bitmap playerW;
public MyRelativeLayout(Context context) {
super(context);
init(context);
}
public MyRelativeLayout(Context context, AttributeSet attrs) {
super(context, attrs);
init(context);
}
public MyRelativeLayout(Context context, AttributeSet attrs, int style) {
super(context, atts, style);
init(context);
}
private void init(final Context context) {
playerW = BitmapFactory.decodeResource(context.getResources(),
R.id.whitePlayer);
}
#Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
canvas.drawBitmap(playerW,0,0,null);
}
}
Then use it in xml as follows
<?xml version="1.0" encoding="utf-8"?>
<your.package.name.package.MyRelativeLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent">
...
all the stuff here
<your.package.name.package.MyRelativeLayout>