Search code examples
javaopencvjavacvkeypoint

Show coordinated for each keypoints using flandmark (Javacv)


I am currently using this example from flandmark using JavaCV. Refer to: https://github.com/bytedeco/javacv-examples/blob/master/flandmark-demo/src/main/java/flandmark/Example1.java. I managed to run the code but is there a way that I could display the coordinated of each of the key point from the face (eye, mouth, nose)? There are around 7/8 key points that could be detected by the flandmark library. Thanks.


Solution

  • You find landmarks in function detectFaceInImage. At the bottom of the same function you see how to draw the detected landmarks on the face:

    flandmark_detect(input, bbox, model, landmarks);
    
    // display landmarks
    cvRectangle(orig, cvPoint(bbox[0], bbox[1]), cvPoint(bbox[2], bbox[3]), CV_RGB(255, 0, 0));
    cvRectangle(orig,
    cvPoint((int) model.bb().get(0), (int) model.bb().get(1)),
    cvPoint((int) model.bb().get(2), (int) model.bb().get(3)), CV_RGB(0, 0, 255));
    cvCircle(orig,
    cvPoint((int) landmarks[0], (int) landmarks[1]), 3, CV_RGB(0, 0, 255), CV_FILLED, 8, 0);
    for (int i = 2; i < 2 * model.data().options().M(); i += 2) {
        cvCircle(orig, cvPoint((int) (landmarks[i]), (int) (landmarks[i + 1])), 3, CV_RGB(255, 0, 0), CV_FILLED, 8, 0);
    }
    

    bbox is a int[] containing the coordinates of the face bounding box as:

    int[0] -> top left x
    int[1] -> top left y
    int[2] -> bottom right x
    int[3] -> bottom right y
    

    landmarks is a double[], containing the coordinates of the points of the landmark in sequence:

    index: 0   1   2   3   ...
    coord: s0x s0y s1x s1y ...
    

    with reference to the image from the flandmark homepage

    enter image description here

    The total number of landmarks is stored in model.data().options().M(). Now you have all the basics to print the coordinates of the landmarks:

    for (int i = 0; i < 2 * model.data().options().M(); i += 2) {
        System.out.println("S" + (i/2) + ": (" + (int)(landmarks[i]) + ", " + (int)(landmarks[i+1]) + ")");
    }