CameraAreaBase

class CameraAreaBase[source]

Bases: object

Overrides the shape of one of the 4 BOX camera detection areas.

The 4 BOX areas (AREA1_BOX..AREA4_BOX) are rectangles by default, edited from the GUI. Subclass this to replace the shape of one of them with a union of polygons and/or circles defined in code (e.g. an L-shaped region), while its status (ALLOWED/NOT_ALLOWED/TRIGGER/OFF) and its threshold keep working exactly as before and stay editable from the GUI — only the position controls for that area are hidden, since the shape is no longer a plain rectangle. Subclass in the project code directory.

__init__() None[source]

Methods

Attributes

name = 'CUSTOM'
area_index = 1
polygons: list[list[list[int]]] = []
circles: list[tuple[int, int, int]] = []
build_mask(height: int, width: int) numpy.ndarray[source]

Rasterize self.polygons and self.circles to a uint8 (h, w) mask, 255 inside else 0.

cv2.fillPoly/cv2.circle handle concave shapes and circles respectively. Override only for a shape that is neither (e.g. build it with numpy slicing).

update_area() None[source]

Marks the cached mask/bbox/contours as stale, so the next call to mask()/bbox()/contains() rebuilds them.

_ensure_cached() only rebuilds automatically when the frame size (self.height/self.width) changes – it has no way to know if self.polygons/self.circles changed instead. Call this after mutating either of those at runtime (e.g. to move the shape to a new position) so the change actually takes effect.

mask() numpy.ndarray[source]

Cached mask, sized self.height x self.width.

bbox() tuple[int, int, int, int][source]

Cached (x1, y1, x2, y2) bounding box of the shape.

contours() list[list[tuple[int, int]]][source]

Cached outer silhouette of the shape, as one point list per disjoint (non-touching) blob.

Traces the rasterized mask instead of self.polygons/self.circles directly, so overlapping or touching pieces merge into a single outline with no interior seams — used to draw the area without the crossing lines a piece-by-piece outline would show.

contains(x: int, y: int) bool[source]

True if pixel (x, y) is inside the area.