在 Android 中使用图像检测裁剪人脸

Crop Face Using Image Detection in Android

我正在尝试检测面部并在矩形图像中裁剪面部部分。我已经完成了面部检测部分,但仍然没有找到任何关于如何裁剪面部部分的帮助。请看看我的代码..!

public class FaceDetect extends Activity {
    private MyImageView mIV;
    private Bitmap mFaceBitmap;
    private int mFaceWidth = 200;
    private int mFaceHeight = 200;
    int cropXinit = 0;
    int cropYint = 0;
    int cropXend = 0;
    int cropYend = 0;
    Bitmap cropedBitmap;
    Bitmap b;
    private static final int MAX_FACES = 1;
    private static String TAG = "FaceDetect";
    private static boolean DEBUG = false;
    protected static final int GUIUPDATE_SETFACE = 999;
    protected Handler mHandler = new Handler() {
        // @Override
        public void handleMessage(Message msg) {
            mIV.invalidate();
            super.handleMessage(msg);
        }
    };
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        mIV = new MyImageView(this);
        setContentView(mIV, new LayoutParams(LayoutParams.WRAP_CONTENT,
                LayoutParams.WRAP_CONTENT));

        // load the photo
        b = ChooseActivity.bitmap;

        mFaceBitmap = b.copy(Bitmap.Config.RGB_565, true);
        b.recycle();

        mFaceWidth = mFaceBitmap.getWidth();
        mFaceHeight = mFaceBitmap.getHeight();
        mIV.setImageBitmap(mFaceBitmap);
        mIV.invalidate();

        setFace();

    }

    public void setFace() {
        FaceDetector fd;
        FaceDetector.Face[] faces = new FaceDetector.Face[MAX_FACES];
        PointF eyescenter = new PointF();
        float eyesdist = 0.0f;
        int[] fpx = null;
        int[] fpy = null;
        int count = 0;

        try {
            fd = new FaceDetector(mFaceWidth, mFaceHeight, MAX_FACES);
            count = fd.findFaces(mFaceBitmap, faces);
        } catch (Exception e) {
            Log.e(TAG, "setFace(): " + e.toString());
            return;
        }

        // check if we detect any faces
        if (count > 0) {
            fpx = new int[count * 2];
            fpy = new int[count * 2];

            for (int i = 0; i < count; i++) {
                try {
                    faces[i].getMidPoint(eyescenter);
                    eyesdist = faces[i].eyesDistance();

                    // set up left eye location
                    fpx[2 * i] = (int) (eyescenter.x - eyesdist / 2);
                    fpy[2 * i] = (int) eyescenter.y;

                    // set up right eye location
                    fpx[2 * i + 1] = (int) (eyescenter.x + eyesdist / 2);
                    fpy[2 * i + 1] = (int) eyescenter.y;

                    if (DEBUG)
                        Log.e(TAG,
                                "setFace(): face "
                                        + i
                                        + ": confidence = "
                                        + faces[i].confidence()
                                        + ", eyes distance = "
                                        + faces[i].eyesDistance()
                                        + ", pose = ("
                                        + faces[i]
                                                .pose(FaceDetector.Face.EULER_X)
                                        + ","
                                        + faces[i]
                                                .pose(FaceDetector.Face.EULER_Y)
                                        + ","
                                        + faces[i]
                                                .pose(FaceDetector.Face.EULER_Z)
                                        + ")" + ", eyes midpoint = ("
                                        + eyescenter.x + "," + eyescenter.y
                                        + ")");
                } catch (Exception e) {
                    Log.e(TAG, "setFace(): face " + i + ": " + e.toString());
                }
            }
        }

        mIV.setDisplayPoints(fpx, fpy, count * 2, 1);
        // if(eyescenter.x -eyesdist >= 0)
        // {
        // cropXinit = (int) (eyescenter.x -eyesdist) ;
        // }
        // else
        // {
        // cropXinit = 0;
        // }
        // if(eyescenter.x +eyesdist <= mFaceWidth)
        // {
        // cropXend = (int) (eyescenter.x +eyesdist) ;
        // }
        // else
        // {
        // cropXend = mFaceWidth;
        // }
        // if(eyescenter.y +eyesdist*2 <= mFaceHeight)
        // {
        // cropYend = (int) (eyescenter.y +eyesdist*2) ;
        // }
        // else
        // {
        // cropYend = mFaceHeight;
        // }
        // if(eyescenter.y -eyesdist >= 0)
        // {
        // cropYint = (int) (eyescenter.y -eyesdist) ;
        // }
        // else
        // {
        // cropYint = 0;
        // }
        // mIV.setImageBitmap(Bitmap.createBitmap(mFaceBitmap,cropXinit,cropYint,cropXend,cropYend));
    }

}

createBitmap(Bitmap source, int x, int y, int width, int height) 接收开始 X 和开始 Y,以及宽度和高度值,而不是结束 X 和结束 Y。如果您将注释掉的代码更改为此,它应该可以工作:

mIV.setImageBitmap(Bitmap.createBitmap(mFaceBitmap,cropXinit,cropYint,cropXend-cropXinit,cropYend-cropYinit));