Capture Signature Using FingerPaint in Android
Posted By : Arpit Sharma | 15-Jan-2013
Today I will blog on how to Capture Signature using FingerPaint in android, you have to follow the given pionts in order to capture signature.
- Create a new SignatureCapture project and replace main.xml code from the given one.
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<Button
android:id="@+id/getSign"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:text="Get Signature" />
<ImageView
android:id="@+id/imageView1"
android:layout_width="200dp"
android:layout_height="200dp"
android:layout_gravity="center"
android:src="@drawable/ic_launcher" />
</LinearLayout>
- Create a new CaptureSignature Activity class and also create capturesignature.xml for layout.
CaptureSignature.java
package com.example.signaturecapture;
import android.app.Activity;
import android.os.Bundle;
public class CaptureSignature extends Activity {
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.capturesignature);
}
}
capturesignature.xml
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical" >
<LinearLayout
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:orientation="horizontal" >
<Button
android:id="@+id/clear"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Clear" />
<Button
android:id="@+id/save"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="save" />
</LinearLayout>
<LinearLayout
android:id="@+id/mysignature"
android:layout_width="fill_parent"
android:layout_height="fill_parent" >
</LinearLayout>
</LinearLayout>
- Now its time to edit MainActivity, initialize the objects and defined their events.
package com.example.signaturecapture;
import android.app.Activity;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
public class MainActivity extends Activity {
Button b1;
ImageView signImage;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
b1 = (Button) findViewById(R.id.getSign);
signImage = (ImageView) findViewById(R.id.imageView1);
b1.setOnClickListener(onButtonClick);
}
Button.OnClickListener onButtonClick = new Button.OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
}
};
}
- Now start CaptureSignature activity on a click of button through intent using startActivityForResult(intent) instead of startActivity(intent) and @override onActivityResult method in MainActivity.(Please configure the CaptureSignature activity in AndroidManifest.xml first).
package com.example.signaturecapture;
import android.app.Activity;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.os.Bundle;
import android.view.View;
import android.widget.Button;
import android.widget.ImageView;
public class MainActivity extends Activity {
Button b1;
ImageView signImage;
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
b1 = (Button) findViewById(R.id.getSign);
signImage = (ImageView) findViewById(R.id.imageView1);
b1.setOnClickListener(onButtonClick);
}
Button.OnClickListener onButtonClick = new Button.OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
Intent i = new Intent(MainActivity.this, CaptureSignature.class);
startActivityForResult(i, 0);
}
};
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
// TODO Auto-generated method stub
if (resultCode == 1) {
Bitmap b = BitmapFactory.decodeByteArray(
data.getByteArrayExtra("byteArray"), 0,
data.getByteArrayExtra("byteArray").length);
signImage.setImageBitmap(b);
}
}
}
- Last but not the least, modify CaptureSignature Activity and return the result data in setResult(1, intent). In CaptureSignature Activity class you have to create an inner class which extends view and draw canvas using paint. The complete code of CaptureSignature Activity class is given below.
CaptureSignature.java
package com.example.signaturecapture;
import java.io.ByteArrayOutputStream;
import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.graphics.Bitmap;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.Path;
import android.graphics.RectF;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.util.AttributeSet;
import android.view.MotionEvent;
import android.view.View;
import android.widget.Button;
import android.widget.LinearLayout;
public class CaptureSignature extends Activity {
signature mSignature;
Paint paint;
LinearLayout mContent;
Button clear, save;
@Override
protected void onCreate(Bundle savedInstanceState) {
// TODO Auto-generated method stub
super.onCreate(savedInstanceState);
setContentView(R.layout.capturesignature);
save = (Button) findViewById(R.id.save);
save.setEnabled(false);
clear = (Button) findViewById(R.id.clear);
mContent = (LinearLayout) findViewById(R.id.mysignature);
mSignature = new signature(this, null);
mContent.addView(mSignature);
save.setOnClickListener(onButtonClick);
clear.setOnClickListener(onButtonClick);
}
Button.OnClickListener onButtonClick = new Button.OnClickListener() {
@Override
public void onClick(View v) {
// TODO Auto-generated method stub
if (v == clear) {
mSignature.clear();
} else if (v == save) {
mSignature.save();
}
}
};
public class signature extends View {
static final float STROKE_WIDTH = 10f;
static final float HALF_STROKE_WIDTH = STROKE_WIDTH / 2;
Paint paint = new Paint();
Path path = new Path();
float lastTouchX;
float lastTouchY;
final RectF dirtyRect = new RectF();
public signature(Context context, AttributeSet attrs) {
super(context, attrs);
paint.setAntiAlias(true);
paint.setColor(Color.BLACK);
paint.setStyle(Paint.Style.STROKE);
paint.setStrokeJoin(Paint.Join.ROUND);
paint.setStrokeWidth(STROKE_WIDTH);
}
public void clear() {
path.reset();
invalidate();
save.setEnabled(false);
}
public void save() {
Bitmap returnedBitmap = Bitmap.createBitmap(mContent.getWidth(),
mContent.getHeight(), Bitmap.Config.ARGB_8888);
Canvas canvas = new Canvas(returnedBitmap);
Drawable bgDrawable = mContent.getBackground();
if (bgDrawable != null)
bgDrawable.draw(canvas);
else
canvas.drawColor(Color.WHITE);
mContent.draw(canvas);
ByteArrayOutputStream bs = new ByteArrayOutputStream();
returnedBitmap.compress(Bitmap.CompressFormat.PNG, 50, bs);
Intent intent = new Intent();
intent.putExtra("byteArray", bs.toByteArray());
setResult(1, intent);
finish();
}
@Override
protected void onDraw(Canvas canvas) {
// TODO Auto-generated method stub
canvas.drawPath(path, paint);
}
@Override
public boolean onTouchEvent(MotionEvent event) {
float eventX = event.getX();
float eventY = event.getY();
save.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);
path.lineTo(historicalX, historicalY);
}
path.lineTo(eventX, eventY);
break;
}
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;
}
private void resetDirtyRect(float eventX, float eventY) {
dirtyRect.left = Math.min(lastTouchX, eventX);
dirtyRect.right = Math.max(lastTouchX, eventX);
dirtyRect.top = Math.min(lastTouchY, eventY);
dirtyRect.bottom = Math.max(lastTouchY, eventY);
}
}
}
Arpit Sharma
Request for Proposal
Cookies are important to the proper functioning of a site. To improve your experience, we use cookies to remember log-in details and provide secure log-in, collect statistics to optimize site functionality, and deliver content tailored to your interests. Click Agree and Proceed to accept cookies and go directly to the site or click on View Cookie Settings to see detailed descriptions of the types of cookies and choose whether to accept certain cookies while on the site.
About Author
Arpit Sharma
Arpit has been developing Android and iPhone applications for a while now and is expert in mobile application development . He excels in developing mobile applications with location based intelligence. Arpit loves Modelling as a hobby.