ภาพรวม
สาธิตการ ติดตามสี (Color Tracking) แบบ Real-time โดยใช้ HSV Color Space, Trackbar ปรับค่า, Morphological Operations และการวาดเส้นทางการเคลื่อนที่
แนวคิดหลัก
- แปลงภาพ BGR → HSV (แยกสีจากความสว่าง)
- ใช้
inRange()กรองสีตามช่วง HSV (ปรับด้วย Trackbar) - Morphological Operations: Erode → Dilate → Dilate → Erode (Opening + Closing) กรอง Noise
- ใช้
Momentsหาจุดกึ่งกลาง (Centroid) และพื้นที่ของวัตถุที่ตรวจจับได้ - ถ้าพื้นที่ > 10000 pixels → วาดเส้นเชื่อมตำแหน่งก่อนหน้า-ปัจจุบัน (
line())
โค้ดตัวอย่าง C++
#include <iostream>
#include <opencv2/highgui/highgui.hpp>
#include <opencv2/imgproc/imgproc.hpp>
using namespace std;
using namespace cv;
int main(int argc, char** argv) {
VideoCapture video_load(0);
namedWindow("Adjust");
// Trackbar สำหรับปรับช่วง HSV
int Hue_Low=0, Hue_High=22, Sat_Low=99, Sat_High=255, Val_Low=0, Val_High=255;
createTrackbar("LowH", "Adjust", &Hue_Low, 179);
createTrackbar("HighH", "Adjust", &Hue_High, 179);
createTrackbar("LowS", "Adjust", &Sat_Low, 255);
createTrackbar("HighS", "Adjust", &Sat_High, 255);
createTrackbar("LowV", "Adjust", &Val_Low, 255);
createTrackbar("HighV", "Adjust", &Val_High, 255);
int Horizontal_Last = -1, Vertical_Last = -1;
Mat temp; video_load.read(temp);
Mat track_motion = Mat::zeros(temp.size(), CV_8UC3); // แผนที่เส้นทาง
while (true) {
Mat actual_Image; video_load.read(actual_Image);
Mat converted_to_HSV; cvtColor(actual_Image, converted_to_HSV, COLOR_BGR2HSV);
Mat adjusted_frame;
inRange(converted_to_HSV, Scalar(Hue_Low, Sat_Low, Val_Low), Scalar(Hue_High, Sat_High, Val_High), adjusted_frame);
// Morphological Operations
erode(adjusted_frame, adjusted_frame, getStructuringElement(MORPH_ELLIPSE, Size(5,5)));
dilate(adjusted_frame, adjusted_frame, getStructuringElement(MORPH_ELLIPSE, Size(5,5)));
dilate(adjusted_frame, adjusted_frame, getStructuringElement(MORPH_ELLIPSE, Size(5,5)));
erode(adjusted_frame, adjusted_frame, getStructuringElement(MORPH_ELLIPSE, Size(5,5)));
Moments detecting_object = moments(adjusted_frame);
double vertical_moment = detecting_object.m01;
double horizontal_moment = detecting_object.m10;
double tracking_area = detecting_object.m00;
if (tracking_area > 10000) {
int posX = horizontal_moment / tracking_area;
int posY = vertical_moment / tracking_area;
if (Horizontal_Last >= 0 && Vertical_Last >= 0 && posX >= 0 && posY >= 0)
line(track_motion, Point(posX, posY), Point(Horizontal_Last, Vertical_Last), Scalar(0,0,255), 2);
Horizontal_Last = posX;
Vertical_Last = posY;
}
imshow("Detected_Object", adjusted_frame);
actual_Image += track_motion; // วาดเส้นทางบนภาพจริง
imshow("Actual", actual_Image);
cout << "Position: " << Horizontal_Last << "," << Vertical_Last << endl;
if (waitKey(30) == 27) break;
}
return 0;
}
ผลลัพธ์
แสดง 2 หน้าต่าง: ภาพ Binary (Detected_Object) และภาพจริงพร้อมเส้นทางสีแดง (Actual)

