/
streamer.go
60 lines (49 loc) · 1.03 KB
/
streamer.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
package streamer
import (
"fmt"
"log"
"net/http"
"sync"
"github.com/mvrilo/cam"
"gocv.io/x/gocv"
)
var Boundary = "CAM"
const payload = "\r\n--%s\r\nContent-Type: image/jpeg\r\nContent-length: %d\r\n\r\n%s\r\n\r\n"
type Streamer struct {
path string
size int
frame []byte
mu sync.Mutex
}
func New(path string) *Streamer {
return &Streamer{
path: path,
}
}
func (s *Streamer) ServeHTTP(w http.ResponseWriter, r *http.Request) {
if r.URL.Path != s.path {
return
}
w.Header().Set("Transfer-Encoding", "deflate")
w.Header().Set("Content-Type", "multipart/x-mixed-replace;boundary="+Boundary)
for {
s.mu.Lock()
fmt.Fprintf(w, payload, Boundary, len(s.frame), s.frame)
s.mu.Unlock()
}
}
func (s *Streamer) Handle(f cam.Frame) {
s.mu.Lock()
defer s.mu.Unlock()
frameData := f.Data()
switch data := frameData.(type) {
case gocv.Mat:
body, err := gocv.IMEncodeWithParams(gocv.JPEGFileExt, data, []int{gocv.IMWriteJpegQuality, 70})
if err != nil {
log.Println(err)
return
}
s.frame = body
default:
}
}