我还没有设法移植威廉链接到的卡尔曼滤波器 c++ 示例,因为并非所有来自 c++ api 的函数都存在于 OpenCV java 包装器中,所以就我所知:
import gab.opencv.*;
import processing.video.*;
import java.awt.*;
import org.opencv.core.*;
import org.opencv.video.*;
int w = 640;
int h = 480;
int hw = w/2;
int hh = h/2;
Capture video;
OpenCV opencv;
/*
Mat img(500, 500, CV_8UC3);
KalmanFilter KF(4, 2, 0);
Mat_<float> state(4, 1); // (x, y, Vx, Vy)
Mat processNoise(4, 1, CV_32F);
Mat_<float> measurement(2,1); measurement.setTo(Scalar(0));
*/
Mat img;
KalmanFilter KF;
Mat processNoise;
MatOfFloat state,measurement;
void setup() {
size(w, h);
video = new Capture(this, hw, hh);
opencv = new OpenCV(this, hw, hh);
opencv.loadCascade(OpenCV.CASCADE_FRONTALFACE);
video.start();
img = new Mat(w,h,CvType.CV_8UC3);
KF = new KalmanFilter(4,2,0,CvType.CV_32F);
state = new MatOfFloat(4,1);
}
void draw() {
background(255);
scale(2);
opencv.loadImage(video);
image(video, 0, 0 );
noFill();
stroke(0, 255, 0);
strokeWeight(3);
Rectangle[] faces = opencv.detect();
if(faces.length > 0)
rect(faces[0].x,faces[0].y,faces[0].width,faces[0].height);
}
void captureEvent(Capture c) {
c.read();
}
statePre
正如您所注意到的,我并没有像或transitionMatrix
不可见的属性那样走得太远。
虽然不一样,但可能有点平均可能会有所帮助:
import gab.opencv.*;
import processing.video.*;
import java.awt.*;
int w = 640;
int h = 480;
int hw = w/2;
int hh = h/2;
Capture video;
OpenCV opencv;
int historySize = 10;
Rectangle[] history;
void setup() {
size(w, h);
video = new Capture(this, hw, hh);
opencv = new OpenCV(this, hw, hh);
opencv.loadCascade(OpenCV.CASCADE_FRONTALFACE);
video.start();
setupHistory();
}
void setupHistory(){
history = new Rectangle[historySize];
for(int i = 0 ; i < historySize ; i++) history[i] = new Rectangle();
}
void keyPressed(){
if(key == 'h' && historySize > 1) {
noLoop();
historySize--;
setupHistory();
loop();
}
if(key == 'H') {
noLoop();
historySize++;
setupHistory();
loop();
}
println(historySize);
}
void draw() {
background(255);
scale(2);
opencv.loadImage(video);
image(video, 0, 0 );
noFill();
stroke(0, 255, 0);
strokeWeight(3);
Rectangle[] faces = opencv.detect();
if(faces.length > 0){
Rectangle f = mousePressed ? average(faces[0]) : faces[0];
rect(f.x,f.y,f.width,f.height);
}
}
void captureEvent(Capture c) {
c.read();
}
Rectangle average(Rectangle newFace){
Rectangle avg = new Rectangle();
for(int i = historySize - 1; i > 0; i--){
history[i] = history[i-1];
avg.x += history[i].x;
avg.y += history[i].y;
avg.width += history[i].width;
avg.height += history[i].height;
}
history[0] = newFace;
avg.x += history[0].x;
avg.y += history[0].y;
avg.width += history[0].width;
avg.height += history[0].height;
avg.x /= historySize;
avg.y /= historySize;
avg.width /= historySize;
avg.height /= historySize;
return avg;
}
按住鼠标可以看到平滑的结果。使用H
键来增加和h
减少历史记录大小。