I am working on canvas application and I have created a canvas with color picker ,Undo,Redo and clear functions and it is also working fine.Now, I want to validate whether the user is currently drawing a line on the background line on the canvas.
For example,
I am having a background image with dotted lines,now I want the user to draw on the dotted lines and I have to validate it whether it is correct or not? Is it possible in canvas and how can I proceed with this?
Could someone give any suggestion about this which will be really help full for me to proceed with next step in my application and my code is here,
public class HomeScreen extends Activity implements ColorPickerDialog.OnColorChangedListener {
public int width;
public int height;
public Arrays paths1;
private Bitmap mBitmap;
private Canvas mCanvas;
private Path mPath;
private Paint mBitmapPaint;
Context context;
private Paint circlePaint;
private Path circlePath;
/* MyView mv; */
DrawingPanel dp;
AlertDialog dialog;
private ArrayList<Path> undonePaths = new ArrayList<Path>();
private ArrayList<Path> paths = new ArrayList<Path>();
FrameLayout frmLayout;
Canvas canvas;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_home_screen);
dp = new DrawingPanel(this);
frmLayout = (FrameLayout) findViewById(R.id.frameLayout);
frmLayout.addView(dp);
((Button) findViewById(R.id.Clear)).setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
paths = new ArrayList<Path>();
if (paths != null)
paths.clear();
if (dp != null)
dp.invalidate();
}
});
((Button) findViewById(R.id.Undo)).setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
if (paths.size() > 0) {
undonePaths.add(paths.remove(paths.size() - 1));
dp.invalidate();
}
}
});
((Button) findViewById(R.id.Redo)).setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
if (undonePaths.size() > 0) {
paths.add(undonePaths.remove(undonePaths.size() - 1));
dp.invalidate();
}
}
});
((Button) findViewById(R.id.letters)).setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
startActivity(new Intent(HomeScreen.this, Letters.class));
}
});
((Button) findViewById(R.id.color)).setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
mCanvas=new Canvas();
new ColorPickerDialog(HomeScreen.this, HomeScreen.this, mPaint.getColor()).show();
}
});
dp.setDrawingCacheEnabled(true);
Bundle extras = getIntent().getExtras();
Integer userName;
if (extras != null) {
userName = extras.getInt("name");
// and get whatever type user account id is
}
dp.setBackgroundResource(R.drawable.atemplate);// set the back
// ground if you wish
mPaint = new Paint();
mPaint.setAntiAlias(true);
mPaint.setDither(true);
mPaint.setColor(0xFFFF0000);
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeJoin(Paint.Join.ROUND);
mPaint.setStrokeCap(Paint.Cap.ROUND);
mPaint.setStrokeWidth(20);
mEmboss = new EmbossMaskFilter(new float[] { 1, 1, 1 }, 0.4f, 6, 3.5f);
// mBlur = new BlurMaskFilter(8, BlurMaskFilter.Blur.NORMAL);
}
private Paint mPaint;
private MaskFilter mEmboss;
private MaskFilter mBlur;
public void colorChanged(int color) {
mPaint.setColor(color);
}
public class DrawingPanel extends View implements OnTouchListener {
private Canvas mCanvas;
private Path mPath;
private Paint mPaint, circlePaint, outercirclePaint;
// private ArrayList<Path> undonePaths = new ArrayList<Path>();
private float xleft, xright, xtop, xbottom;
public DrawingPanel(Context context) {
super(context);
setFocusable(true);
setFocusableInTouchMode(true);
this.setOnTouchListener(this);
circlePaint = new Paint();
mPaint = new Paint();
outercirclePaint = new Paint();
outercirclePaint.setAntiAlias(false);
circlePaint.setAntiAlias(false);
mPaint.setAntiAlias(false);
mPaint.setColor(0xFF000000);
outercirclePaint.setColor(0x44FFF000);
circlePaint.setColor(0xF57F35);
outercirclePaint.setStyle(Paint.Style.FILL_AND_STROKE);
circlePaint.setStyle(Paint.Style.FILL);
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeJoin(Paint.Join.MITER);
mPaint.setStrokeCap(Paint.Cap.ROUND);
mPaint.setStrokeWidth(10);
outercirclePaint.setStrokeWidth(10);
mCanvas = new Canvas();
mPath = new Path();
paths.add(mPath);
}
public void colorChanged(int color) {
mPaint.setColor(color);
}
#Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
}
#Override
protected void onDraw(Canvas canvas) {
for (Path p : paths) {
canvas.drawPath(p, mPaint);
}
}
private float mX, mY;
private static final float TOUCH_TOLERANCE = 0;
private void touch_start(float x, float y) {
mPath.reset();
mPath.moveTo(x, y);
mX = x;
mY = y;
}
private void touch_move(float x, float y) {
float dx = Math.abs(x - mX);
float dy = Math.abs(y - mY);
if (dx >= TOUCH_TOLERANCE || dy >= TOUCH_TOLERANCE) {
mPath.quadTo(mX, mY, (x + mX) / 2, (y + mY) / 2);
mX = x;
mY = y;
}
}
private void touch_up() {
mPath.lineTo(mX, mY);
// commit the path to our offscreen
mCanvas.drawPath(mPath, mPaint);
// kill this so we don't double draw
mPath = new Path();
paths.add(mPath);
}
#Override
public boolean onTouch(View arg0, MotionEvent event) {
float x = event.getX();
float y = event.getY();
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
// if (x <= cx+circleRadius+5 && x>= cx-circleRadius-5) {
// if (y<= cy+circleRadius+5 && cy>= cy-circleRadius-5){
// paths.clear();
// return true;
// }
// }
touch_start(x, y);
invalidate();
break;
case MotionEvent.ACTION_MOVE:
touch_move(x, y);
invalidate();
break;
case MotionEvent.ACTION_UP:
touch_up();
invalidate();
break;
}
return true;
}
}
}
Are you thinking to create a app like pattern locker which are in android devices, try to implement like this way.
#Override
public boolean onTouchEvent(MotionEvent event) {
// MotionEvent object holds X-Y values
if(event.getAction() == MotionEvent.ACTION_DOWN) {
String text = "You click at x = " + event.getX() + " and y = " + event.getY();
Toast.makeText(this, text, Toast.LENGTH_LONG).show();
}
return super.onTouchEvent(event);
}
this link may help
Your programming skills are good. Difficulty here depends on how complicated the lines are. Have you tried saving the position of the dots? and then compare it to getX and getY when the user presses the screen.
Related
I am working in canvas related application and everything is working fine except clear all function.
I have used this code for creating canvas and it is also having a erase operation but it is erasing manually.
public class CharactersCanvas extends Activity {
public int width;
public int height;
public Arrays paths1;
private Bitmap mBitmap;
private Canvas mCanvas;
private Path mPath;
private Paint mBitmapPaint;
Context context;
private Paint circlePaint;
private Path circlePath;
static List<Integer> listFlag;
/* MyView mv; */
DrawingPanel dp;
AlertDialog dialog;
private ArrayList<Path> undonePaths = new ArrayList<Path>();
public ArrayList<Path> paths = new ArrayList<Path>();
private ArrayList<String> step = new ArrayList<String>();
FrameLayout frmLayout;
Canvas canvas;
protected static ImageView imageView;
private Integer frameIndex = 0;
public int res;
#SuppressLint("NewApi")
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.canvas_screen);
dp = new DrawingPanel(this);
frmLayout = (FrameLayout) findViewById(R.id.frameLayout1);
imageView=(ImageView) findViewById(R.id.imageView5);
frmLayout.addView(dp);
Bundle bundle = this.getIntent().getExtras();
res = bundle.getInt("resourseInt");
imageView.setImageResource(res);
frameIndex = (bundle != null && bundle.getInt("image") != 0) ? HomeScreen.characters.indexOf(bundle.getInt("image")) : frameIndex;
System.out.println(" Blank " + frameIndex);
frmLayout.setBackgroundResource((int)HomeScreen.characters.get(frameIndex));
/*
* if(){ dp.setBackgroundResource(R.drawable.atemplate); }
*/
((Button) findViewById(R.id.clear_buttonn))
.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
paths = new ArrayList<Path>();
if (paths != null)
paths.clear();
if(dp !=null)
dp.invalidate();
}
});
((Button) findViewById(R.id.next_buttonn))
.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
paths = new ArrayList<Path>();
if (frameIndex < (HomeScreen.characters.size() - 1)) {
if (paths != null)
paths.clear();
if (dp != null)
dp.invalidate();
System.out.println(" Size is "
+ HomeScreen.characters.size());
frmLayout
.setBackgroundResource((int) HomeScreen.characters
.get(frameIndex != HomeScreen.characters
.size() ? ++frameIndex
: frameIndex));
}
}
});
((Button) findViewById(R.id.previous_buttonn))
.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
if (frameIndex >= 0) {
paths = new ArrayList<Path>();
if (paths != null)
paths.clear();
if (dp != null)
dp.invalidate();
frmLayout
.setBackgroundResource((int) HomeScreen.characters
.get(frameIndex == 0 ? frameIndex
: --frameIndex));
}
}
});
((Button) findViewById(R.id.letters_buttonn))
.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
MediaPlayer mPlayer = MediaPlayer.create(
CharactersCanvas.this, R.raw.one_sound);
mPlayer.start();
Intent intent = new Intent(getApplicationContext(),
CharactersGridView.class);
intent.putExtra("resourseInt", res);
// integerList is
// ArrayList<Integer>
startActivity(intent);
/*
* startActivity(new Intent(CharactersCanvas.this,
* CharactersGridView.class));
*/
}
});
((Button) findViewById(R.id.home_buttonn))
.setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
MediaPlayer mPlayer = MediaPlayer.create(
CharactersCanvas.this, R.raw.one_sound);
mPlayer.start();
startActivity(new Intent(CharactersCanvas.this,
HomeScreen.class));
finish();
}
});
}
private Paint mPaint;
private MaskFilter mEmboss;
private MaskFilter mBlur;
public class DrawingPanel extends View implements OnTouchListener {
private Canvas mCanvas;
private Path mPath;
private Paint mPaint, circlePaint, outercirclePaint;
// private ArrayList<Path> undonePaths = new ArrayList<Path>();
private float xleft, xright, xtop, xbottom;
public DrawingPanel(Context context) {
super(context);
setFocusable(true);
setFocusableInTouchMode(true);
this.setOnTouchListener(this);
circlePaint = new Paint();
mPaint = new Paint();
outercirclePaint = new Paint();
outercirclePaint.setAntiAlias(false);
circlePaint.setAntiAlias(false);
mPaint.setAntiAlias(false);
mPaint.setColor(0xFFFF0000);
outercirclePaint.setColor(0x44FFF000);
circlePaint.setColor(0xF57F35);
outercirclePaint.setStyle(Paint.Style.FILL_AND_STROKE);
circlePaint.setStyle(Paint.Style.FILL);
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeJoin(Paint.Join.MITER);
mPaint.setStrokeCap(Paint.Cap.ROUND);
mPaint.setStrokeWidth(10);
outercirclePaint.setStrokeWidth(10);
mCanvas = new Canvas();
mPath = new Path();
paths.add(mPath);
}
public void colorChanged(int color) {
mPaint.setColor(color);
}
#Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
}
#Override
protected void onDraw(Canvas canvas) {
if (paths != null && paths.size() > 0) {
for (Path p : paths) {
canvas.drawPath(p, mPaint);
}
}
}
private float mX, mY;
private static final float TOUCH_TOLERANCE = 0;
private void touch_start(float x, float y) {
mPath.reset();
mPath.moveTo(x, y);
mX = x;
mY = y;
}
private void touch_move(float x, float y) {
float dx = Math.abs(x - mX);
float dy = Math.abs(y - mY);
if (dx >= TOUCH_TOLERANCE || dy >= TOUCH_TOLERANCE) {
mPath.quadTo(mX, mY, (x + mX) / 2, (y + mY) / 2);
mX = x;
mY = y;
}
}
private void touch_up() {
mPath.lineTo(mX, mY);
// commit the path to our offscreen
mCanvas.drawPath(mPath, mPaint);
// kill this so we don't double draw
mPath = new Path();
paths.add(mPath);
}
#Override
public boolean onTouch(View arg0, MotionEvent event) {
float x = event.getX();
float y = event.getY();
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
// if (x <= cx+circleRadius+5 && x>= cx-circleRadius-5) {
// if (y<= cy+circleRadius+5 && cy>= cy-circleRadius-5){
// paths.clear();
// return true;
// }
// }
touch_start(x, y);
invalidate();
break;
case MotionEvent.ACTION_MOVE:
touch_move(x, y);
invalidate();
break;
case MotionEvent.ACTION_UP:
touch_up();
invalidate();
break;
}
return true;
}
}
}
I want to clear all the scribles using a single button .How to do this ?Any idea will be really usefull.
to clear the canvas's content you could draw a color,
canvas.drawColor(Color.TRANSPARENT)
for instance.
I want to clear all the drawn content in the canvas .I tried several ways and none was clicked for me yet.How to clear all the content in canvas android using clear button?
I have clear button to clear the content in canvas android.But I clearly did not know how to delete the content.I am having undo and redo button which is working fine except this clear button.Could some one tell me how to use this clear button and delete the content? My code is here.
public class MainActivity extends Activity {
private ArrayList<Path> undonePaths = new ArrayList<Path>();
private ArrayList<Path> paths = new ArrayList<Path>();
/*
* private Button alphabetsButton; private Button lettersButton; private
* Button clearButton;
*/
private FrameLayout frmLayout;
Canvas canvas;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
frmLayout = (FrameLayout) findViewById(R.id.frameLayout);
final DrawingPanel dp = new DrawingPanel(MainActivity.this);
frmLayout.addView(dp);
/*
* alphabetsButton=(Button) findViewById(R.id.button1);
* lettersButton=(Button) findViewById(R.id.button2);
*
*
*
* alphabetsButton.setOnClickListener(new OnClickListener() {
*
* #Override public void onClick(View v) { // TODO Auto-generated method
* stub startActivity(new Intent(MainActivity.this,Letters.class));
* finish(); } });
*/
((Button) findViewById(R.id.Clear)).setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
paths = new ArrayList<Path>();
paths.clear();
}
});
((Button) findViewById(R.id.Undo)).setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
if (paths.size() > 0) {
undonePaths.add(paths.remove(paths.size() - 1));
dp.invalidate();
}
}
});
((Button) findViewById(R.id.Redo)).setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
// TODO Auto-generated method stub
if (undonePaths.size() > 0) {
paths.add(undonePaths.remove(undonePaths.size() - 1));
dp.invalidate();
}
}
});
}
class DrawingPanel extends View implements OnTouchListener {
private Canvas mCanvas;
private Path mPath;
private Paint mPaint, circlePaint, outercirclePaint;
private Bitmap mBitmap;
private int width;
private int height;
// private ArrayList<Path> undonePaths = new ArrayList<Path>();
private float xleft, xright, xtop, xbottom;
public DrawingPanel(Context context) {
super(context);
setFocusable(true);
setFocusableInTouchMode(true);
this.setOnTouchListener(this);
circlePaint = new Paint();
mPaint = new Paint();
outercirclePaint = new Paint();
outercirclePaint.setAntiAlias(false);
circlePaint.setAntiAlias(false);
mPaint.setAntiAlias(false);
mPaint.setColor(0xFF000000);
outercirclePaint.setColor(0x44FFF000);
circlePaint.setColor(0xF57F35);
outercirclePaint.setStyle(Paint.Style.FILL_AND_STROKE);
circlePaint.setStyle(Paint.Style.FILL);
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeJoin(Paint.Join.MITER);
mPaint.setStrokeCap(Paint.Cap.ROUND);
mPaint.setStrokeWidth(20);
outercirclePaint.setStrokeWidth(15);
mCanvas = new Canvas();
mPath = new Path();
paths.add(mPath);
}
public void colorChanged(int color) {
mPaint.setColor(color);
}
#Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
}
#Override
protected void onDraw(Canvas canvas) {
for (Path p : paths) {
canvas.drawPath(p, mPaint);
}
}
private float mX, mY;
private static final float TOUCH_TOLERANCE = 0;
private void touch_start(float x, float y) {
mPath.reset();
mPath.moveTo(x, y);
mX = x;
mY = y;
}
private void touch_move(float x, float y) {
float dx = Math.abs(x - mX);
float dy = Math.abs(y - mY);
if (dx >= TOUCH_TOLERANCE || dy >= TOUCH_TOLERANCE) {
mPath.quadTo(mX, mY, (x + mX) / 2, (y + mY) / 2);
mX = x;
mY = y;
}
}
private void touch_up() {
mPath.lineTo(mX, mY);
// commit the path to our offscreen
mCanvas.drawPath(mPath, mPaint);
// kill this so we don't double draw
mPath = new Path();
paths.add(mPath);
}
#Override
public boolean onTouch(View arg0, MotionEvent event) {
float x = event.getX();
float y = event.getY();
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
// if (x <= cx+circleRadius+5 && x>= cx-circleRadius-5) {
// if (y<= cy+circleRadius+5 && cy>= cy-circleRadius-5){
// paths.clear();
// return true;
// }
// }
touch_start(x, y);
invalidate();
break;
case MotionEvent.ACTION_MOVE:
touch_move(x, y);
invalidate();
break;
case MotionEvent.ACTION_UP:
touch_up();
invalidate();
break;
}
return true;
}
}
}
may you should avoid to instantiate paths again before calling clear(), otherwise you'll call clear() on an empty ArrayList:
((Button) findViewById(R.id.Clear)).setOnClickListener(new OnClickListener() {
#Override
public void onClick(View v) {
if (paths != null)
paths.clear();
if (dp != null)
dp.invalidate();
}
});
Looks like the paths array list is persisting, try this code:
private ArrayList<Path> _graphics = new ArrayList<Path>()
#Override
public void onClick(View v) {
clear();
}
Bitmap mBitmap;
Paint mPaint;
Canvas mCanvas;
int width,height;
public void clear()
{
_graphics.removeAll(_graphics);
mBitmap = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
path = new Path();
invalidate();
}
You can try this:
#Override
public void onClick(DialogInterface dialog, int which) {
mCanvas.drawColor(0, PorterDuff.Mode.CLEAR);
//paths.clear();
//.destroyDrawingCache();
mPath.reset();
dp.invalidate();
}
Hi using myview in one class.am drawing some lines,after that if am clicking button then am going to some other class,then again i am coming back to previous class,but here i drawn lines is not there,but in my case i need to show that drawn lines when i come back to previous activity...can you any one suggest me..thnkyou
MainActivity
public class MainActivity extends Activity {
MyView myview;
RelativeLayout rl;
Button b1;
public boolean action = false;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
b1=(Button)findViewById(R.id.button1);
b1.setOnClickListener(new OnClickListener() {
public void onClick(View arg0) {
// TODO Auto-generated method stub
Intent i=new Intent(MainActivity.this,Activity2.class);
startActivity(i);
}
});
rl = (RelativeLayout) findViewById(R.id.layout);
mPaint = new Paint();
mPaint.setAntiAlias(true);
mPaint.setDither(true);
// mPaint.setColor(0xFFFF0000);
mPaint.setColor(Color.BLACK);
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeJoin(Paint.Join.ROUND);
mPaint.setStrokeCap(Paint.Cap.ROUND);
mPaint.setStrokeWidth(6);
myview = new MyView(this);
myview.setId(004);
RelativeLayout.LayoutParams lp6 = new RelativeLayout.LayoutParams(
LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
myview.setLayoutParams(lp6);
// myview.setBackgroundResource(R.drawable.booklet);
lp6.setMargins(10, 100, 10, 10);
// lp6.setMargins(25, 50, 8,70);
rl.addView(myview, lp6);
}
private Paint mPaint;
private Bitmap mBitmap;
public void colorChanged(int color) {
mPaint.setColor(color);
}
public class MyView extends View {
private Canvas mCanvas;
private Path mPath;
private Paint mBitmapPaint;
public MyView(Context context) {
super(context);
// TODO Auto-generated constructor stub
mPath = new Path();
mBitmapPaint = new Paint(Paint.DITHER_FLAG);
}
#Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
mBitmap = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);
mCanvas = new Canvas(mBitmap);
// clearAllResources();
}
#Override
protected void onDraw(Canvas canvas) {
if (action) {
invalidate();
}
canvas.drawBitmap(mBitmap, 0, 0, mBitmapPaint);
canvas.drawPath(mPath, mPaint);
}
private float mX, mY;
private final float TOUCH_TOLERANCE = 2;
private void touch_start(float x, float y) {
mPath.reset();
mPath.moveTo(x, y);
mX = x;
mY = y;
}
private void touch_move(float x, float y) {
float dx = Math.abs(x - mX);
float dy = Math.abs(y - mY);
if (dx >= TOUCH_TOLERANCE || dy >= TOUCH_TOLERANCE) {
mPath.quadTo(mX, mY, (x + mX) / 2, (y + mY) / 2);
mX = x;
mY = y;
}
}
private void touch_up() {
mPath.lineTo(mX, mY);
// commit the path to our offscreen
mCanvas.drawPath(mPath, mPaint);
// kill this so we don't double draw
mPath.reset();
}
#Override
public boolean onTouchEvent(MotionEvent event) {
float x = event.getX();
float y = event.getY();
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
touch_start(x, y);
invalidate();
break;
case MotionEvent.ACTION_MOVE:
touch_move(x, y);
invalidate();
break;
case MotionEvent.ACTION_UP:
touch_up();
invalidate();
break;
}
return true;
}
}
}
Activity2
public class Activity2 extends Activity {
Button b1;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.acticity2);
b1=(Button)findViewById(R.id.button1);
b1.setOnClickListener(new OnClickListener() {
public void onClick(View arg0) {
// TODO Auto-generated method stub
Intent i=new Intent(Activity2.this,MainActivity.class);
startActivityForResult(i, 0);
}
});
}
}
Create a line class that has following properties
float startX, float startY, float stopX, float stopY, Paint paint
Then create List to contain your line instances. Each time you create a line, create a new line instance, set its data and add it to the list. In onDraw, iterate through the list and draw each line with the data you stored.
Problem with your code is that you a launching a new instance of activity whenever button is clicked.
Instead of startActivity() , try calling finish() from Activity2.
OR you can use setFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
to bring previous instance of MainActivity to front.
public void onClick(View v) {
Intent intent = new Intent(getApplicationContext(),MainActivity.class);
//finish(); OR
intent.setFlags(Intent.FLAG_ACTIVITY_REORDER_TO_FRONT);
startActivity(intent);
}
/I got the following code:
public class SketchActivity extends Activity implements OnClickListener, OnSeekBarChangeListener {
private MyView myView;
private Button clearBtn;
private ToggleButton embossBtn, blurBtn, eraseBtn, srcaBtn;
private RelativeLayout layout, layout2;
private TextView penSizeTxt;
SharedPreferences pref;
private Preview preview;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN);
setContentView(R.layout.activity_main);
init();
preview = new Preview(this);
layout2 = (RelativeLayout) findViewById(R.id.paint_layout2);
layout = (RelativeLayout) findViewById(R.id.paint_layout);
layout.addView(preview);
new Handler().postDelayed(new Runnable() {
#Override
public void run() {
myView = new MyView(SketchActivity.this, layout.getWidth(), layout.getHeight());
layout2.addView(myView);
layout2.bringToFront();
}
}, 50);
mPaint = new Paint();
mPaint.setAntiAlias(true);
mPaint.setDither(true);
mPaint.setColor(0xFF000000);
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeJoin(Paint.Join.ROUND);
mPaint.setStrokeCap(Paint.Cap.ROUND);
mPaint.setStrokeWidth(5);
mEmboss = new EmbossMaskFilter(new float[] { 1, 1, 1 }, 0.4f, 6, 3.5f);
mBlur = new BlurMaskFilter(8, BlurMaskFilter.Blur.NORMAL);
}
private void init() {
clearBtn = (Button) findViewById(R.id.clearBtn);
embossBtn = (ToggleButton) findViewById(R.id.embossBtn);
blurBtn = (ToggleButton) findViewById(R.id.blurBtn);
eraseBtn = (ToggleButton) findViewById(R.id.eraseBtn);
srcaBtn = (ToggleButton) findViewById(R.id.srcatopBtn);
clearBtn.setOnClickListener(this);
embossBtn.setOnClickListener(this);
blurBtn.setOnClickListener(this);
eraseBtn.setOnClickListener(this);
srcaBtn.setOnClickListener(this);
}
private static Paint mPaint;
private MaskFilter mEmboss;
private MaskFilter mBlur;
public void colorChanged(int color) {
mPaint.setColor(color);
}
private void setToggleOf() {
embossBtn.setChecked(false);
eraseBtn.setChecked(false);
blurBtn.setChecked(false);
srcaBtn.setChecked(false);
}
#Override
public void onClick(View v) {
if (v.getId() == embossBtn.getId()) {
if (mPaint.getMaskFilter() != mEmboss) {
setToggleOf();
mPaint.setXfermode(null);
mPaint.setAlpha(0xFF);
mPaint.setMaskFilter(mEmboss);
embossBtn.setChecked(true);
} else {
mPaint.setMaskFilter(null);
embossBtn.setChecked(false);
}
} else if (v.getId() == blurBtn.getId()) {
if (mPaint.getMaskFilter() != mBlur) {
setToggleOf();
mPaint.setXfermode(null);
mPaint.setAlpha(0xFF);
mPaint.setMaskFilter(mBlur);
blurBtn.setChecked(true);
} else {
mPaint.setMaskFilter(null);
blurBtn.setChecked(false);
}
} else if (v.getId() == eraseBtn.getId()) {
if (eraseBtn.isChecked()) {
setToggleOf();
eraseBtn.setChecked(true);
mPaint.setMaskFilter(null);
mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
} else {
mPaint.setMaskFilter(null);
mPaint.setXfermode(null);
mPaint.setAlpha(0xFF);
}
} else if (v.getId() == srcaBtn.getId()) {
if (srcaBtn.isChecked()) {
setToggleOf();
mPaint.setMaskFilter(null);
srcaBtn.setChecked(true);
mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.SRC_ATOP));
mPaint.setAlpha(0x80);
} else {
mPaint.setMaskFilter(null);
mPaint.setXfermode(null);
mPaint.setAlpha(0xFF);
}
}
else if (v.getId() == clearBtn.getId()) {
layout2.removeAllViews();
myView = new MyView(SketchActivity.this, layout.getWidth(), layout.getHeight());
layout2.addView(myView);
}
}
public class MyView extends View {
private static final float MINP = 0.25f;
private static final float MAXP = 0.75f;
private Bitmap mBitmap;
private Canvas mCanvas;
private Path mPath;
private Paint mBitmapPaint;
Bitmap bitmap;
int x = 0;
int y = 0;
int r = 0;
public MyView(Context c, int width, int height) {
super(c);
WindowManager wm = (WindowManager) c.getSystemService(Context.WINDOW_SERVICE);
Display display = wm.getDefaultDisplay();
int w = display.getWidth(); // deprecated
int h = display.getHeight();
// setFocusable(true);
// setBackgroundResource(R.drawable.download);
// setting paint
mPath = new Path();
mPaint = new Paint();
mPaint.setAlpha(0);
mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.DST_IN));
mPaint.setAntiAlias(true);
mPaint.setMaskFilter(new BlurMaskFilter(10, BlurMaskFilter.Blur.NORMAL));
mBitmapPaint = new Paint(Paint.DITHER_FLAG);
this.getContext().getResources();
Bitmap bm = BitmapFactory.decodeResource(getResources(), R.drawable.smoke);
Bitmap bm2 = getResizedBitmap(bm, h, w);
// converting image bitmap into mutable bitmap
bitmap = bm2.createBitmap(w, h, Config.ARGB_8888);
mCanvas = new Canvas();
mCanvas.setBitmap(bitmap); // drawXY will result on that Bitmap
mCanvas.drawBitmap(bm2, 0, 0, null);
}
#Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
}
#Override
protected void onDraw(Canvas canvas) {
//mCanvas.drawCircle(x, y, r, mPaint);
// canvas.drawBitmap(bitmap, 0, 0, null);
canvas.drawBitmap(bitmap, 0, 0, mBitmapPaint);
canvas.drawPath(mPath, mPaint);
super.onDraw(canvas);
}
private float mX, mY;
private static final float TOUCH_TOLERANCE = 4;
private void touch_start(float x, float y) {
mPath.reset();
mPath.moveTo(x, y);
// mPath.lineTo(x, y);
// mCanvas.drawPoint(x, y, mPaint);
mX = x;
mY = y;
}
private void touch_move(float x, float y) {
float dx = Math.abs(x - mX);
float dy = Math.abs(y - mY);
if ((dx >= TOUCH_TOLERANCE) || (dy >= TOUCH_TOLERANCE)) {
mPath.quadTo(mX, mY, (x + mX) / 2, (y + mY) / 2);
mX = x;
mY = y;
}
// invalidate();
}
private void touch_up() {
mPath.lineTo(mX, mY);
// commit the path to our offscreen
mCanvas.drawPath(mPath, mPaint);
// kill this so we don't double draw
mPath.reset();
}
#Override
public boolean onTouchEvent(MotionEvent event) {
float x = event.getX();
float y = event.getY();
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
touch_start(x, y);
invalidate();
break;
case MotionEvent.ACTION_MOVE:
touch_move(x, y);
invalidate();
break;
case MotionEvent.ACTION_UP:
touch_up();
invalidate();
break;
}
return true;
}
public Bitmap getImage() {
return mBitmap;
}
}
#Override
public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
// TODO Auto-generated method stub
penSizeTxt.setText(String.valueOf(progress + 2));
}
#Override
public void onStartTrackingTouch(SeekBar seekBar) {
// TODO Auto-generated method stub
}
#Override
public void onStopTrackingTouch(SeekBar seekBar) {
// TODO Auto-generated method stub
}
public Bitmap getResizedBitmap(Bitmap bm, int newHeight, int newWidth) {
int width = bm.getWidth();
int height = bm.getHeight();
float scaleWidth = ((float) newWidth) / width;
float scaleHeight = ((float) newHeight) / height;
// CREATE A MATRIX FOR THE MANIPULATION
Matrix matrix = new Matrix();
// RESIZE THE BIT MAP
matrix.postScale(scaleWidth, scaleHeight);
// RECREATE THE NEW BITMAP
Bitmap resizedBitmap = Bitmap.createBitmap(bm, 0, 0, width, height, matrix, false);
return resizedBitmap;
}
}
I want it to clear the second layout and show the content of the camera, on touch. So that if i make a curved line with my finger on the screen it would set those pixels to alpha, and see the camera from the back layout. The problem is that if for example, i make a curved line, the app erases the content of that curve too. So that if i would make a circle with my finger it would erase the content of the circle too, not only the margin.
A screenshot with how it looks: http://imgur.com/5gjNB
onCreate i had:
mPaint = new Paint();
mPaint.setAntiAlias(true);
mPaint.setDither(true);
mPaint.setColor(0xFF000000);
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeJoin(Paint.Join.ROUND);
mPaint.setStrokeCap(Paint.Cap.ROUND);
mPaint.setStrokeWidth(5);
And then on my View i had:
mPaint = new Paint();
mPaint.setAlpha(0);
mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.DST_IN));
mPaint.setAntiAlias(true);
mPaint.setMaskFilter(new BlurMaskFilter(10, BlurMaskFilter.Blur.NORMAL));
Overriding the mPaint, and that's what made it not work properly. By deleting the second:
mPaint = new Paint();
I made it work
hi i need perform undo operation in paints.some one suggest use command pattern but i am not getting command pattern.is there any solution is there. help me how to do undo.
i draw paints using below code.
BookType3.class:
public class BookType3 extends Activity implements OnClickListener{
MyView myview;
int counter=0;
private Paint mBitmapPaint;
TextView t1,t2;
private Bitmap mBitmap;
public static boolean action=false;
Button back,erase,undo,save,home;
int image1,image2,image3;
private Canvas mCanvas;
RelativeLayout relative;
RelativeLayout.LayoutParams lp6,lp7;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
setContentView(R.layout.booktype1);
List<String> names = Arrays.asList("a","b","c");
relative=(RelativeLayout)findViewById(R.id.relative3);
myview = new MyView(this);
myview.setId(004);
lp6 = new RelativeLayout.LayoutParams(
RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
myview.setLayoutParams(lp6);
myview.setBackgroundResource(R.drawable.writingsapce);
undo=(Button)findViewById(R.id.undobutton);
undo.setOnClickListener(this);
mPaint = new Paint();
mPaint.setAntiAlias(true);
mPaint.setDither(true);
mPaint.setColor(Color.BLACK);
mPaint.setStyle(Paint.Style.STROKE);
mPaint.setStrokeJoin(Paint.Join.ROUND);
mPaint.setStrokeCap(Paint.Cap.ROUND);
mPaint.setStrokeWidth(4);
String s1="";
t1=(TextView)findViewById(R.id.button1);
t1.setOnClickListener(this);
t2=(TextView)findViewById(R.id.button2);
t2.setOnClickListener(this);
relative.addView(myview,lp6);
}
private Paint mPaint;
public class MyView extends View{
private Path mPath;
public MyView(Context context) {
super(context);
// TODO Auto-generated constructor stub
mPath = new Path();
mBitmapPaint = new Paint(Paint.DITHER_FLAG);
}
#Override
protected void onSizeChanged(int w, int h, int oldw, int oldh) {
super.onSizeChanged(w, h, oldw, oldh);
mBitmap = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);
mCanvas = new Canvas(mBitmap);
}
#Override
protected void onDraw(Canvas canvas) {
canvas.drawBitmap(mBitmap, 0, 0, mBitmapPaint);
canvas.drawPath(mPath, mPaint);
if(action)
{
invalidate();
}
}
private float mX, mY;
private static final float TOUCH_TOLERANCE = 2;
private void touch_start(float x, float y) {
mPath.reset();
mPath.moveTo(x, y);
mX = x;
mY = y;
}
private void touch_move(float x, float y) {
float dx = Math.abs(x - mX);
float dy = Math.abs(y - mY);
if (dx >= TOUCH_TOLERANCE || dy >= TOUCH_TOLERANCE) {
mPath.quadTo(mX, mY, (x + mX)/2, (y + mY)/2);
mX = x;
mY = y;
}
}
private void touch_up() {
mPath.lineTo(mX, mY);
// commit the path to our offscreen
mCanvas.drawPath(mPath, mPaint);
// kill this so we don't double draw
mPath.reset();
}
#Override
public boolean onTouchEvent(MotionEvent event) {
int x = (int) event.getX();
int y = (int) event.getY();
Log.i("x",""+event.getX());
Log.i("y",""+event.getY());
switch (event.getAction()) {
case MotionEvent.ACTION_DOWN:
touch_start(x, y);
invalidate();
break;
case MotionEvent.ACTION_MOVE:
touch_move(x, y);
invalidate();
break;
case MotionEvent.ACTION_UP:
touch_up();
invalidate();
break;
}
return true;
}
}
public void onClick(View v) {
// TODO Auto-generated method stub
if(v==t1)
{
mPaint.setColor(Color.RED);
t30.setText("A");
t31.setText("a");
t32.setText("Aa");
t30.setTextColor(Color.RED);
t31.setTextColor(Color.RED);
t32.setTextColor(Color.RED);
try{
mBitmap.eraseColor(android.graphics.Color.TRANSPARENT);
Canvas Canvas=new Canvas(mBitmap);
action=true;
myview.onDraw(Canvas);
}catch(IllegalStateException ie){
ie.printStackTrace();
}
}
if(v==t2)
{
t30.setTextColor(Color.BLUE);
t31.setTextColor(Color.BLUE);
t32.setTextColor(Color.BLUE);
mPaint.setColor(Color.BLUE);
t30.setText("B");
t31.setText("b");
t32.setText("Bb");
try{
mBitmap.eraseColor(android.graphics.Color.TRANSPARENT);
Canvas Canvas=new Canvas(mBitmap);
action=true;
myview.onDraw(Canvas);
}catch(IllegalStateException ie){
ie.printStackTrace();
}
}
if(v==undo)
{
}
}
}
Instead of the Command Pattern, I think you should use the Memento Pattern, which is designed for things like undo and redo. There are two ways to implement this pattern. Either by saving deltas, or by saving entire states. Saving states would be easiest in your situation, but it has larger memory footprint. This would involve writing a bitmap to the filesystem every time the user modifies the main bitmap. You could decide on a constant number of undo steps (e.g. 10), and then save the 10 most recent bitmaps. Saving deltas would be more complex. You would implement it by recording the touch events, color, brush, etc. of each paint action. You can then playback and/or rollback individual actions using the motion events. Saving deltas would take significantly less memory, and you would be able to store many more actions and you wouldn't have to write to the filesystem.
private Slate mSlate;
private TiledBitmapCanvas mTiledCanvas;
public void clickUndo(View unused) {
mSlate.undo();
}
public void undo() {
if (mTiledCanvas == null) {
Log.v(TAG, "undo before mTiledCanvas inited");
}
mTiledCanvas.step(-1);
invalidate();
}