Frame counter resets on a consistent interval.

This commit is contained in:
Scott 2020-01-08 11:31:09 +10:30
parent 0b95041d4f
commit 4b28558924
1 changed files with 66 additions and 65 deletions

View File

@ -84,70 +84,71 @@ func (m *MOGFilter) Write(f []byte) (int, error) {
m.hold[hfCount] = f
hfCount++
return 0, nil
} else {
img, err := gocv.IMDecode(f, gocv.IMReadColor)
if err != nil {
return 0, fmt.Errorf("image can't be decoded: %w", err)
}
defer img.Close()
imgDelta := gocv.NewMat()
defer imgDelta.Close()
// Seperate foreground and background.
m.bs.Apply(img, &imgDelta)
// Threshold imgDelta.
gocv.Threshold(imgDelta, &imgDelta, 25, 255, gocv.ThresholdBinary)
// Remove noise.
gocv.Erode(imgDelta, &imgDelta, m.knl)
gocv.Dilate(imgDelta, &imgDelta, m.knl)
// Fill small holes.
gocv.Dilate(imgDelta, &imgDelta, m.knl)
gocv.Erode(imgDelta, &imgDelta, m.knl)
// Find contours and reject ones with a small area.
var contours [][]image.Point
allContours := gocv.FindContours(imgDelta, gocv.RetrievalExternal, gocv.ChainApproxSimple)
for _, c := range allContours {
if gocv.ContourArea(c) > m.area {
contours = append(contours, c)
}
}
// Draw debug information.
if m.debug {
for _, c := range contours {
rect := gocv.BoundingRect(c)
gocv.Rectangle(&img, rect, color.RGBA{0, 0, 255, 0}, 1)
}
if len(contours) > 0 {
gocv.PutText(&img, "Motion", image.Pt(32, 32), gocv.FontHersheyPlain, 2.0, color.RGBA{255, 0, 0, 0}, 2)
}
m.windows[0].IMShow(img)
m.windows[1].IMShow(imgDelta)
m.windows[0].WaitKey(1)
}
// Don't write to destination if there is no motion.
if len(contours) == 0 {
return 0, nil
}
// Write to destination, past 4 frames then current frame.
for i, h := range m.hold {
_, err := m.dst.Write(h)
m.hold[i] = nil
if err != nil {
return 0, err
}
}
hfCount = 0
return m.dst.Write(f)
}
hfCount = 0
img, err := gocv.IMDecode(f, gocv.IMReadColor)
if err != nil {
return 0, fmt.Errorf("image can't be decoded: %w", err)
}
defer img.Close()
imgDelta := gocv.NewMat()
defer imgDelta.Close()
// Seperate foreground and background.
m.bs.Apply(img, &imgDelta)
// Threshold imgDelta.
gocv.Threshold(imgDelta, &imgDelta, 25, 255, gocv.ThresholdBinary)
// Remove noise.
gocv.Erode(imgDelta, &imgDelta, m.knl)
gocv.Dilate(imgDelta, &imgDelta, m.knl)
// Fill small holes.
gocv.Dilate(imgDelta, &imgDelta, m.knl)
gocv.Erode(imgDelta, &imgDelta, m.knl)
// Find contours and reject ones with a small area.
var contours [][]image.Point
allContours := gocv.FindContours(imgDelta, gocv.RetrievalExternal, gocv.ChainApproxSimple)
for _, c := range allContours {
if gocv.ContourArea(c) > m.area {
contours = append(contours, c)
}
}
// Draw debug information.
if m.debug {
for _, c := range contours {
rect := gocv.BoundingRect(c)
gocv.Rectangle(&img, rect, color.RGBA{0, 0, 255, 0}, 1)
}
if len(contours) > 0 {
gocv.PutText(&img, "Motion", image.Pt(32, 32), gocv.FontHersheyPlain, 2.0, color.RGBA{255, 0, 0, 0}, 2)
}
m.windows[0].IMShow(img)
m.windows[1].IMShow(imgDelta)
m.windows[0].WaitKey(1)
}
// Don't write to destination if there is no motion.
if len(contours) == 0 {
return 0, nil
}
// Write to destination, past 4 frames then current frame.
for i, h := range m.hold {
_, err := m.dst.Write(h)
m.hold[i] = nil
if err != nil {
return 0, err
}
}
return m.dst.Write(f)
}