Add webcam functionality to the agent's API and web interface. Implement endpoints for listing available webcams and capturing frames, along with corresponding UI elements for device selection and frame display. Update OpenAPI specification to include new webcam features, enhancing user interaction with webcam devices.
This commit is contained in:
@@ -0,0 +1,71 @@
|
||||
package webcam
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"encoding/binary"
|
||||
"errors"
|
||||
"fmt"
|
||||
"image"
|
||||
"image/jpeg"
|
||||
"image/png"
|
||||
)
|
||||
|
||||
func encodeImage(img image.Image, format string, quality int) ([]byte, string, error) {
|
||||
var buf bytes.Buffer
|
||||
if format == "jpeg" {
|
||||
err := jpeg.Encode(&buf, img, &jpeg.Options{Quality: quality})
|
||||
return buf.Bytes(), "image/jpeg", err
|
||||
}
|
||||
err := png.Encode(&buf, img)
|
||||
return buf.Bytes(), "image/png", err
|
||||
}
|
||||
|
||||
func decodeBMP(data []byte) (*image.RGBA, error) {
|
||||
if len(data) < 54 || data[0] != 'B' || data[1] != 'M' {
|
||||
return nil, errors.New("invalid bitmap")
|
||||
}
|
||||
offset := binary.LittleEndian.Uint32(data[10:14])
|
||||
width := int(int32(binary.LittleEndian.Uint32(data[18:22])))
|
||||
heightSigned := int32(binary.LittleEndian.Uint32(data[22:26]))
|
||||
bits := binary.LittleEndian.Uint16(data[28:30])
|
||||
compression := binary.LittleEndian.Uint32(data[30:34])
|
||||
if compression != 0 {
|
||||
return nil, fmt.Errorf("unsupported bmp compression %d", compression)
|
||||
}
|
||||
if bits != 24 && bits != 32 {
|
||||
return nil, fmt.Errorf("unsupported bmp bit depth %d", bits)
|
||||
}
|
||||
topDown := heightSigned < 0
|
||||
height := int(heightSigned)
|
||||
if height < 0 {
|
||||
height = -height
|
||||
}
|
||||
if width <= 0 || height <= 0 || int(offset) >= len(data) {
|
||||
return nil, errors.New("invalid bmp dimensions")
|
||||
}
|
||||
bpp := int(bits / 8)
|
||||
rowSize := (width*bpp + 3) &^ 3
|
||||
need := int(offset) + rowSize*height
|
||||
if need > len(data) {
|
||||
return nil, errors.New("truncated bmp")
|
||||
}
|
||||
img := image.NewRGBA(image.Rect(0, 0, width, height))
|
||||
for y := 0; y < height; y++ {
|
||||
srcY := y
|
||||
if !topDown {
|
||||
srcY = height - 1 - y
|
||||
}
|
||||
row := data[int(offset)+srcY*rowSize:]
|
||||
for x := 0; x < width; x++ {
|
||||
i := x * bpp
|
||||
b, g, r := row[i], row[i+1], row[i+2]
|
||||
a := byte(255)
|
||||
if bpp == 4 {
|
||||
a = row[i+3]
|
||||
}
|
||||
off := (y*width + x) * 4
|
||||
img.Pix[off], img.Pix[off+1], img.Pix[off+2], img.Pix[off+3] = r, g, b, a
|
||||
}
|
||||
}
|
||||
return img, nil
|
||||
}
|
||||
Reference in New Issue
Block a user