Search code examples
androidbitmapimageviewandroid-canvasdraw

Android: Draw text on ImageView with finger touch


i completed the drawing text on ImageView and i saved the final image in sd card. My problem is, when i am touching the screen to draw the text, my image in the ImageView is disappearing.

Code

import java.io.File;
import java.io.FileOutputStream;
import android.net.Uri;
import android.os.Bundle;
import android.os.Environment;
import android.os.StrictMode;
import android.annotation.SuppressLint;
import android.app.Activity;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.Bitmap.CompressFormat;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.view.MotionEvent;
import android.view.View;
import android.view.View.OnClickListener;
import android.view.View.OnTouchListener;
import android.widget.Button;
import android.widget.ImageView;
import android.widget.Toast;

public class DrawTextOnImgActivity extends Activity {
    private Button btn_save, btn_resume;
    private ImageView iv_canvas;
    private Bitmap baseBitmap;
    private Canvas canvas;
    private Paint paint;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_draw_text_on_img);

        // The initialization of a brush, brush width is 5, color is red
        paint = new Paint();
        paint.setStrokeWidth(5);
        paint.setColor(Color.RED);

        iv_canvas = (ImageView) findViewById(R.id.imageView1);
        btn_save = (Button) findViewById(R.id.btn_save);
        btn_resume = (Button) findViewById(R.id.btn_resume);

        btn_save.setOnClickListener(click);
        btn_resume.setOnClickListener(click);
        iv_canvas.setOnTouchListener(touch);
    }

    private View.OnTouchListener touch = new OnTouchListener() {
        // Coordinate definition finger touch
        float startX;
        float startY;

        @SuppressLint("ClickableViewAccessibility")
        @Override
        public boolean onTouch(View v, MotionEvent event) {
            switch (event.getAction()) {
            // Press the user action
            case MotionEvent.ACTION_DOWN:
                // The first drawing initializes the memory image, specify the background is white
                if (baseBitmap == null) {
                    baseBitmap = Bitmap.createBitmap(iv_canvas.getWidth(),
                            iv_canvas.getHeight(), Bitmap.Config.ARGB_8888);
                    canvas = new Canvas(baseBitmap);
                    canvas.drawColor(Color.WHITE);
                }
                // Recording began to touch point coordinate
                startX = event.getX();
                startY = event.getY();
                break;
                // The user's finger on the screen of mobile action
            case MotionEvent.ACTION_MOVE:
                // Record the coordinates of the mobile point
                float stopX = event.getX();
                float stopY = event.getY();

                //According to the coordinates of the two points, drawing lines
                canvas.drawLine(startX, startY, stopX, stopY, paint);

                // Update start point
                startX = event.getX();
                startY = event.getY();

                // The pictures to the ImageView
                iv_canvas.setImageBitmap(baseBitmap);
                break;
            case MotionEvent.ACTION_UP:

                break;
            default:
                break;
            }
            return true;
        }
    };
    private View.OnClickListener click = new OnClickListener() {

        @Override
        public void onClick(View v) {

            switch (v.getId()) {
            case R.id.btn_save:
                saveBitmap();
                break;
            case R.id.btn_resume:
                resumeCanvas();
                break;
            default:
                break;
            }
        }
    };

    /**
     * Save the image to the SD card.
     */
     protected void saveBitmap() {
        try {
            // Save the image to the SD card.

            File folder = new File(Environment.getExternalStorageDirectory() + "/DrawTextOnImg");

            if (!folder.exists()) {
                folder.mkdir();
            }

            File file = new File(Environment.getExternalStorageDirectory()+"/DrawTextOnImg/tempImg.png");

            FileOutputStream stream = new FileOutputStream(file);
            baseBitmap.compress(CompressFormat.PNG, 100, stream);
            Toast.makeText(DrawTextOnImgActivity.this, "Save the picture of success", Toast.LENGTH_SHORT).show();

            // Android equipment Gallery application will only at boot time scanning system folder
            // The simulation of a media loading broadcast, for the preservation of images can be viewed in Gallery
            Intent intent = new Intent();
            intent.setAction(Intent.ACTION_MEDIA_MOUNTED);
            intent.setData(Uri.fromFile(Environment.getExternalStorageDirectory()));
            sendBroadcast(intent);
        } catch (Exception e) {
            Toast.makeText(DrawTextOnImgActivity.this, "Save failed", Toast.LENGTH_SHORT).show();
            e.printStackTrace();
        }
     }

     /**
      * Clear the drawing board
      */
     protected void resumeCanvas() {
         // Manually clear the drawing board, to create a drawing board
         if (baseBitmap != null) {
             baseBitmap = Bitmap.createBitmap(iv_canvas.getWidth(), iv_canvas.getHeight(), Bitmap.Config.ARGB_8888);
             canvas = new Canvas(baseBitmap);
             canvas.drawColor(Color.WHITE);
             iv_canvas.setImageBitmap(baseBitmap);
             Toast.makeText(DrawTextOnImgActivity.this, "Clear the drawing board, can be re started drawing", Toast.LENGTH_SHORT).show();
         }
     }
}

Manifest

<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<protected-broadcast android:name="android.intent.action.MEDIA_MOUNTED" />

By using this code i am writing the text on ImageView but image in the ImageView is disappearing. So, please help me to write the text on image of ImageView


Solution

  • I achieved it by fallowing this code

    DrawTextOnImgActivity

    import java.io.File;
    import java.io.FileOutputStream;
    
    import android.net.Uri;
    import android.os.Bundle;
    import android.os.Environment;
    import android.provider.MediaStore.Images;
    import android.util.Log;
    import android.view.View;
    import android.view.View.OnClickListener;
    import android.widget.Button;
    import android.widget.ImageView;
    import android.widget.Toast;
    import android.app.Activity;
    import android.content.Intent;
    import android.graphics.Bitmap;
    import android.graphics.Bitmap.CompressFormat;
    import android.graphics.Canvas;
    
    public class DrawTextOnImgActivity extends Activity {
    
        ImageView ivDrawImg;
    
        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_draw_text_on_img);
    
            ivDrawImg = (ImageView) findViewById(R.id.iv_draw);
            Button btnSave = (Button) findViewById(R.id.btn_save);
            Button btnResume = (Button) findViewById(R.id.btn_resume);
    
    
    
    
            btnSave.setOnClickListener(new OnClickListener() {
    
                @Override
                public void onClick(View v) {
    
                    saveImg();
    
                }
            });
    
            btnResume.setOnClickListener(new OnClickListener() {
    
                @Override
                public void onClick(View v) {
    
                }
            });
    
    
    
         }
    
    
        private void saveImg(){
    
            Bitmap image = Bitmap.createBitmap(ivDrawImg.getWidth(), ivDrawImg.getHeight(), Bitmap.Config.RGB_565); 
            ivDrawImg.draw(new Canvas(image)); 
    
            String uri = Images.Media.insertImage(getContentResolver(), image, "title", null); 
    
            Log.e("uri", uri);
    
    
    
            try {
                // Save the image to the SD card.
    
                File folder = new File(Environment.getExternalStorageDirectory() + "/DrawTextOnImg");
    
                if (!folder.exists()) {
                    folder.mkdir();
                    //folder.mkdirs();  //For creating multiple directories
                }
    
                File file = new File(Environment.getExternalStorageDirectory()+"/DrawTextOnImg/tempImg.png");
    
                FileOutputStream stream = new FileOutputStream(file);
                image.compress(CompressFormat.PNG, 100, stream);
                Toast.makeText(DrawTextOnImgActivity.this, "Picture saved", Toast.LENGTH_SHORT).show();
    
                // Android equipment Gallery application will only at boot time scanning system folder
                // The simulation of a media loading broadcast, for the preservation of images can be viewed in Gallery
    
                /*Intent intent = new Intent();
                intent.setAction(Intent.ACTION_MEDIA_MOUNTED);
                intent.setData(Uri.fromFile(Environment.getExternalStorageDirectory()));
                sendBroadcast(intent);*/
    
            } catch (Exception e) {
                Toast.makeText(DrawTextOnImgActivity.this, "Save failed", Toast.LENGTH_SHORT).show();
                e.printStackTrace();
            }
    
        }
    }
    

    DrawView

    import java.util.ArrayList;
    import java.util.List;
    
    import android.annotation.SuppressLint;
    import android.content.Context;
    import android.graphics.Canvas;
    import android.graphics.Color;
    import android.graphics.Paint;
    import android.graphics.Path;
    import android.util.AttributeSet;
    import android.view.MotionEvent;
    import android.widget.ImageView;
    
    public class DrawView extends ImageView {
    
        private int color = Color.parseColor("#0000FF");
        private float width = 4f;
        private List<Holder> holderList = new ArrayList<Holder>();
    
        private class Holder {      
            Path path;
            Paint paint;
    
            Holder(int color, float width) {
                path = new Path();
                paint = new Paint();
                paint.setAntiAlias(true);
                paint.setStrokeWidth(width);
                paint.setColor(color);
                paint.setStyle(Paint.Style.STROKE);
                paint.setStrokeJoin(Paint.Join.ROUND);
                paint.setStrokeCap(Paint.Cap.ROUND);
            }
        }
    
        public DrawView(Context context) {
            super(context);
            init();
        }
    
        public DrawView(Context context, AttributeSet attrs) {
            super(context, attrs);
            init();
        }
    
        public DrawView(Context context, AttributeSet attrs, int defStyle) {
            super(context, attrs, defStyle);
            init();
        }
    
        private void init() {
            holderList.add(new Holder(color, width));
        }
    
        @Override
        protected void onDraw(Canvas canvas) {
            super.onDraw(canvas);
            for (Holder holder : holderList) {
                canvas.drawPath(holder.path, holder.paint);
            }
        }
    
        @SuppressLint("ClickableViewAccessibility")
        @Override
        public boolean onTouchEvent(MotionEvent event) {
            float eventX = event.getX();
            float eventY = event.getY();
    
            switch (event.getAction()) {
                case MotionEvent.ACTION_DOWN:
                    holderList.add(new Holder(color,width));
                    holderList.get(holderList.size() - 1).path.moveTo(eventX, eventY);
                    return true;
                case MotionEvent.ACTION_MOVE:
                    holderList.get(holderList.size() - 1).path.lineTo(eventX, eventY);
                    break;
                case MotionEvent.ACTION_UP:
                    break;
                default:
                    return false;
            }
    
            invalidate();
            return true;
        }
    
        public void resetPaths() {
            for (Holder holder : holderList) {
                holder.path.reset();
            }
            invalidate();
        }
    
        public void setBrushColor(int color) {
            this.color = color;
        }
    
        public void setWidth(float width) {
            this.width = width;
        }
    }
    

    Layout (activity_draw_text_on_img)

    <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
        xmlns:tools="http://schemas.android.com/tools"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:background="#FFFFFF" >
    
        <RelativeLayout
            android:layout_width="match_parent"
            android:layout_height="250dp"
            android:layout_centerInParent="true"
            android:background="#FFFFFF" >
    
            <com.app.drawtextonimg.DrawView
                android:id="@+id/iv_draw"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                android:adjustViewBounds="true"
                android:src="@drawable/rajamouli" />
        </RelativeLayout>
    
        <Button
            android:id="@+id/btn_save"
            android:layout_width="match_parent"
            android:layout_height="40dp"
            android:layout_alignParentBottom="true"
            android:background="#000000"
            android:text="@string/save"
            android:textColor="#FFFFFF" />
    
        <Button
            android:id="@+id/btn_resume"
            android:layout_width="match_parent"
            android:layout_height="40dp"
            android:background="#000000"
            android:text="@string/resume"
            android:textColor="#FFFFFF" />
    
    </RelativeLayout>
    

    Manifest file

    <uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
    <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
    

    Project link