Eraser в Android View

Я создаю приложение для рисования на холсте. Для рисования я установил цвет пера в черный цвет.

Для кнопки пера

int black = Color.BLACK; mDrawPaint = new DrawPaint(Capture.this, null,black); 

Где DrawPaint extends View

Теперь, чтобы создать ластик, я просто изменил цвет пера на белый, что является цветом фона холста. Как это

Для кнопки стирания

  int white = Color.WHITE; mDrawPaint = new DrawPaint(Capture.this, null,white); 

Но опять же, если я выберу кнопку пера, которая имеет черный цвет пера и рисует что-то на холсте, она снова автоматически перерисовывает предыдущую краску, которую я нарисовал, прежде чем стирать ее. Также ластик стирает большую прямоугольную область. Пожалуйста, объясните мне, что происходит не так. Спасибо.

Вот конструктор DrawPaint

  public DrawPaint(Context context, AttributeSet attrs, int color) { super(context, attrs); this.destroyDrawingCache(); paint.setAntiAlias(true); paint.setColor(color); paint.setStyle(Paint.Style.STROKE); paint.setStrokeJoin(Paint.Join.ROUND); paint.setStrokeWidth(STROKE_WIDTH); } public boolean onTouchEvent(MotionEvent event) { eventX = event.getX(); eventY = event.getY(); button1.setEnabled(true); switch (event.getAction()) { case MotionEvent.ACTION_DOWN: path.moveTo(eventX, eventY); lastTouchX = eventX; lastTouchY = eventY; return true; case MotionEvent.ACTION_MOVE: case MotionEvent.ACTION_UP: resetDirtyRect(eventX, eventY); int historySize = event.getHistorySize(); for (int i = 0; i < historySize; i++) { float historicalX = event.getHistoricalX(i); float historicalY = event.getHistoricalY(i); expandDirtyRect(historicalX, historicalY); path.lineTo(historicalX, historicalY); } path.lineTo(eventX, eventY); break; default: debug("Ignored touch event: " + event.toString()); return false; } invalidate((int) (dirtyRect.left - HALF_STROKE_WIDTH), (int) (dirtyRect.top - HALF_STROKE_WIDTH), (int) (dirtyRect.right + HALF_STROKE_WIDTH), (int) (dirtyRect.bottom + HALF_STROKE_WIDTH)); lastTouchX = eventX; lastTouchY = eventY; return true; } 

Для Eraser вы можете использовать этот код …

 mPaint.setMaskFilter(null); mPaint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR)); 

И об этом квадратном цвете …

Проверьте это .. это лучший пример для рисования холста с стиранием, размытием и эффектом Emboss …

 public class FingerText extends Activity implements ColorPickerDialog.OnColorChangedListener { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(new MyView(this)); mPaint = new Paint(); mPaint.setAntiAlias(true); mPaint.setDither(true); //this is the line that sets the initial pen color mPaint.setColor(inkColor); mPaint.setStyle(Paint.Style.STROKE); mPaint.setStrokeJoin(Paint.Join.ROUND); mPaint.setStrokeCap(Paint.Cap.ROUND); mPaint.setStrokeWidth(2); } private Paint mPaint; private Bitmap mBitmap; private boolean inkChosen; private int bgColor = 0xFFFFFFFF; //set initial bg color var to white private int inkColor = 0xFF000000; //set initial ink color var to black public void colorChanged(int color) { //This is the implementation of the interface from colorpickerdialog.java if (inkChosen){ mPaint.setColor(color); inkColor = color; } else { mBitmap.eraseColor (color); bgColor = color; //set the color to the user's last ink color choice mPaint.setColor(inkColor); } } public class MyView extends View { private Canvas mCanvas; private Path mPath; private Paint mBitmapPaint; public MyView(Context c) { super(c); mBitmap = Bitmap.createBitmap(320, 480, Bitmap.Config.ARGB_8888); //this sets the bg color for the bitmap mBitmap.eraseColor (bgColor); mCanvas = new Canvas(mBitmap); 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); } @Override protected void onDraw(Canvas canvas) { //this is the line that changes the bg color in the initial canvas canvas.drawColor(bgColor); canvas.drawBitmap(mBitmap, 0, 0, mBitmapPaint); canvas.drawPath(mPath, mPaint); } 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); 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; } } private static final int BG_COLOR_ID = Menu.FIRST; private static final int INK_MENU_ID = Menu.FIRST + 1; private static final int CLEAR_MENU_ID = Menu.FIRST + 2; private static final int ERASER_MENU_ID = Menu.FIRST + 3; private static final int SEND_MENU_ID = Menu.FIRST + 4; @Override public boolean onCreateOptionsMenu(Menu menu) { super.onCreateOptionsMenu(menu); menu.add(0, BG_COLOR_ID, 0, "Background Color").setShortcut('3', 'b'); menu.add(0, INK_MENU_ID, 0, "Ink Color").setShortcut('4', 'c'); menu.add(0, CLEAR_MENU_ID, 0, "Clear All").setShortcut('5', 'e'); menu.add(0, ERASER_MENU_ID, 0, "Eraser").setShortcut('6', 'x'); menu.add(0, SEND_MENU_ID, 0, "Send").setShortcut('7', 's'); /**** Is this the mechanism to extend with filter effects? Intent intent = new Intent(null, getIntent().getData()); intent.addCategory(Intent.CATEGORY_ALTERNATIVE); menu.addIntentOptions( Menu.ALTERNATIVE, 0, new ComponentName(this, NotesList.class), null, intent, 0, null); *****/ return true; } @Override public boolean onPrepareOptionsMenu(Menu menu) { super.onPrepareOptionsMenu(menu); return true; } @Override public boolean onOptionsItemSelected(MenuItem item) { mPaint.setXfermode(null); mPaint.setAlpha(0xFF); switch (item.getItemId()) { case BG_COLOR_ID: new ColorPickerDialog(this, this, mPaint.getColor()).show(); inkChosen = false; return true; case INK_MENU_ID: new ColorPickerDialog(this, this, mPaint.getColor()).show(); //remember the user's last ink choice color so we can revert after eraser //to background color change -- otherwise ink is last bg color inkColor = mPaint.getColor(); inkChosen = true; return true; case CLEAR_MENU_ID: mBitmap.eraseColor (bgColor); return true; case ERASER_MENU_ID: //set pen color to bg color for 'erasing' mPaint.setColor(bgColor); return true; case SEND_MENU_ID: /* TODO need to decide whether to save image locally * and how to make it available if so. really only need to * save if we want to let users view later, or pick a * previous message to send again */ // this try-catch block creates a private file and an // inputstream pointing to it for reading FileInputStream ifs; try { FileOutputStream fs = openFileOutput("message_image", Context.MODE_PRIVATE); mBitmap.compress(CompressFormat.PNG, 100, fs); ifs = openFileInput("message_image"); } catch (FileNotFoundException e) { // TODO Auto-generated catch block e.printStackTrace(); return true; } // inserts file pointed to by ifs into image gallery String url = Images.Media.insertImage(getContentResolver(), BitmapFactory.decodeStream(ifs), "Message image1", "Message image"); // alternative: inserts mBitmap into image gallery /* String url = Images.Media.insertImage(getContentResolver(), mBitmap, "Message image1", "Message image"); */ // creates the Intent to open the messaging app // with the image at url attached Intent sendIntent = new Intent(Intent.ACTION_SEND); sendIntent.putExtra("sms_body", "Message created using FingerText"); sendIntent.putExtra(Intent.EXTRA_STREAM, Uri.parse(url)); sendIntent.setType("image/png"); startActivity(sendIntent); /* TODO delete the image from the content provider * following line deletes the image, but too soon! */ // getContentResolver().delete(Uri.parse(url), null, null); //this resets canvas after send //could also reset to last user settings w/o var resets bgColor = 0xFFFFFFFF; //set bg color var back to white inkColor = 0xFF000000; //set ink color var back to black mBitmap.eraseColor (bgColor); return true; } return super.onOptionsItemSelected(item); } 

}

Intereting Posts
WebViewCoreThread, используемый admob AdView, использует высокий CPU даже в том случае, если родительская активность приостановлена ​​ Как установить разделитель (до нуля) настраиваемого макета ListFragment Что лучше? Большое количество вызовов веб-сервисов (SOAP-сообщений) или большой объем данных в одном сообщении Soap? Android: Flush DNS Уточнение в row_id, возвращаемое выражением insert sqlite Как изменить положение пунктов меню на панели действий Диалог пользовательских предупреждений не центрирован по вертикали на Android Могу ли я нажимать кнопку программно для предопределенного намерения? Как я могу воспроизводить видео MP4 по прямой ссылке в Android-плеерах Android? Adb shell dumpsys meminfo – В чем смысл каждой ячейки его вывода? Android Image Recognition API / библиотека (не в облаке) Сбой интерфейса Javascript для Android Proguard Изменение исходного кода эмулятора Android Расширение плавающей кнопки действия notifyDataSetChanged () не обновляет ListActivity автоматически