Skip to content

Commit c674f18

Browse files
james-kwongsamfreund
authored andcommitted
Add YoloV11 OBB
1 parent 56bbae1 commit c674f18

15 files changed

+547
-34
lines changed

CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,7 @@ add_library(
8686
src/main/native/cpp/preprocess.cc
8787
src/main/native/cpp/postprocess_v5.cc
8888
src/main/native/cpp/postprocess_v8_11.cc
89+
src/main/native/cpp/postprocess_v11obb.cc
8990
)
9091

9192
target_link_libraries(
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
cage
4.24 MB
Binary file not shown.

out2.png

-675 KB
Loading

src/main/java/org/photonvision/rknn/RknnJNI.java

Lines changed: 23 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -18,23 +18,41 @@
1818
package org.photonvision.rknn;
1919

2020
import org.opencv.core.Point;
21-
import org.opencv.core.Rect2d;
21+
import org.opencv.core.RotatedRect;
22+
import org.opencv.core.Size;
2223

2324
public class RknnJNI {
2425
public static enum ModelVersion {
2526
YOLO_V5,
2627
YOLO_V8,
27-
YOLO_V11
28+
YOLO_V11,
29+
YOLO_V11OBB
2830
}
2931

3032
public static class RknnResult {
31-
public RknnResult(int left, int top, int right, int bottom, float conf, int class_id) {
33+
/**
34+
* Creates an RknnResult object representing one detected object
35+
*
36+
* @param cx The x position of the center point of the bounding box
37+
* @param cy The y position of the center point of the bounding box
38+
* @param width The width of the bounding rectangle
39+
* @param height The height of the bounding rectangle
40+
* @param angle The angle, in radians, in which the rectangle is rotated about its center point.
41+
* 0 indicates an axis-aligned bbox
42+
* @param conf The confidence of the detection
43+
* @param class_id The class of the detection
44+
*/
45+
public RknnResult(
46+
int cx, int cy, int width, int height, float angle, float conf, int class_id) {
3247
this.conf = conf;
3348
this.class_id = class_id;
34-
this.rect = new Rect2d(new Point(left, top), new Point(right, bottom));
49+
50+
// OpenCV uses degrees
51+
this.rect =
52+
new RotatedRect(new Point(cx, cy), new Size(width, height), Math.toDegrees(angle));
3553
}
3654

37-
public final Rect2d rect;
55+
public final RotatedRect rect;
3856
public final float conf;
3957
public final int class_id;
4058

src/main/native/cpp/main_test.cc

Lines changed: 38 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,11 @@ int main_test(ModelVersion version)
1717
} else if (version == ModelVersion::YOLO_V11){
1818
printf("Starting with version 11\n");
1919
wrapper = new YoloV11Model("note-robot-yolov11s-quant.rknn", 3, 0);
20+
} else if (version == ModelVersion::YOLO_V11OBB){
21+
printf("Starting with version 11OBB\n");
22+
wrapper = new YoloV11OBBModel("cageconverted-640-640-yolov11obbn.rknn", 1, 0);
23+
// wrapper = new YoloV11OBBModel("best_yolo11obbn_cage_CONVERTED_FP32.rknn", 1, 0);
24+
// wrapper = new YoloV11OBBModel("epochbestREAL-1024-1024-yolov11obbm.rknn", 2, 0);
2025
} else {
2126
printf("Unknown version\n");
2227
return 1;
@@ -26,7 +31,9 @@ int main_test(ModelVersion version)
2631

2732
for (int j = 0; j < 1; j++) {
2833
cv::Mat img;
29-
img = cv::imread("robots.png");
34+
img = cv::imread("test_cage_2_rotated.jpg");
35+
36+
// cv::resize(img, img, cv::Size(1024, 1024));
3037

3138
DetectionFilterParams params {
3239
.nms_thresh = 0.45,
@@ -37,27 +44,39 @@ int main_test(ModelVersion version)
3744
std::cout << "Count: " << ret.count << std::endl;
3845
for (int i = 0; i < ret.count; ++i) {
3946
std::cout << "ID: " << ret.results[i].id << " conf " << ret.results[i].obj_conf << " @ "
40-
<< ret.results[i].box.top << " - "
41-
<< ret.results[i].box.left << " - "
42-
<< ret.results[i].box.bottom << " - "
43-
<< ret.results[i].box.right << " - "
47+
<< "cx: " << ret.results[i].obb.cx << " - "
48+
<< "cy: " << ret.results[i].obb.cy << " - "
49+
<< "width: " << ret.results[i].obb.width << " - "
50+
<< "height: " << ret.results[i].obb.height << " - "
51+
<< "angle: " << ret.results[i].obb.angle << " - "
4452
<< std::endl;
4553

4654
auto *det_result = &(ret.results[i]);
4755

48-
int x1 = det_result->box.left;
49-
int y1 = det_result->box.top;
50-
int x2 = det_result->box.right;
51-
int y2 = det_result->box.bottom;
56+
int cx = det_result->obb.cx;
57+
int cy = det_result->obb.cy;
58+
int w = det_result->obb.width;
59+
int h = det_result->obb.height;
60+
float angle_rad = det_result->obb.angle;
61+
float angle_deg = angle_rad * 180.0f / CV_PI; // RotatedRect expects degrees
62+
63+
cv::RotatedRect rrect(cv::Point2f((float)cx, (float)cy), cv::Size2f((float)w, (float)h), angle_deg);
64+
65+
cv::Point2f pts2f[4];
66+
rrect.points(pts2f); // fill 4 corners
67+
68+
std::vector<cv::Point> box_pts(4);
69+
for (int k = 0; k < 4; ++k) box_pts[k] = pts2f[k]; // round to ints
5270

53-
cv::rectangle(
54-
img, cv::Rect(x1, y1, x2-x1, y2-y1), (0,255,0), 3
55-
);
71+
std::vector<std::vector<cv::Point>> contour(1, box_pts);
72+
cv::drawContours(img, contour, 0, cv::Scalar(0, 255, 0), 3);
73+
74+
// place label near top left of the rotated box
75+
cv::Rect bbox = cv::boundingRect(box_pts);
5676

57-
// draw_rectangle(&src_image, x1, y1, x2 - x1, y2 - y1, COLOR_BLUE, 3);
5877
char text[256];
5978
sprintf(text, "id%i %.1f%%", det_result->id, det_result->obj_conf * 100);
60-
cv::putText(img, text, {x1, y1 + 10}, cv::FONT_ITALIC, 0.6, {100, 255, 0});
79+
cv::putText(img, text, {bbox.x, bbox.y + 10}, cv::FONT_ITALIC, 1.25, {100, 255, 0});
6180
}
6281

6382
cv::imwrite("out2.png", img);
@@ -76,6 +95,10 @@ int main() {
7695
// threads.emplace_back(std::thread([]() {main_test("../note-640-640-yolov5s.rknn");}));
7796
// for (auto& th : threads) th.join();
7897

79-
main_test(ModelVersion::YOLO_V8);
98+
main_test(ModelVersion::YOLO_V11OBB);
99+
// main_test(ModelVersion::YOLO_V11);
100+
// main_test(ModelVersion::YOLO_V8);
80101
// main_test(ModelVersion::YOLO_V5);
102+
103+
return 0;
81104
}

0 commit comments

Comments
 (0)