diff --git a/web/src/components/Table.jsx b/web/src/components/Table.jsx
index a80f7a508..eb5a1431c 100644
--- a/web/src/components/Table.jsx
+++ b/web/src/components/Table.jsx
@@ -14,9 +14,9 @@ export function Thead({ children, className, ...attrs }) {
);
}
-export function Tbody({ children, className, ...attrs }) {
+export function Tbody({ children, className, reference, ...attrs }) {
return (
-
+
{children}
);
@@ -30,9 +30,10 @@ export function Tfoot({ children, className = '', ...attrs }) {
);
}
-export function Tr({ children, className = '', ...attrs }) {
+export function Tr({ children, className = '', reference, ...attrs }) {
return (
@@ -49,9 +50,9 @@ export function Th({ children, className = '', colspan, ...attrs }) {
);
}
-export function Td({ children, className = '', colspan, ...attrs }) {
+export function Td({ children, className = '', reference, colspan, ...attrs }) {
return (
- |
+ |
{children}
|
);
diff --git a/web/src/index.css b/web/src/index.css
index 2278ef964..eb81700c2 100644
--- a/web/src/index.css
+++ b/web/src/index.css
@@ -36,5 +36,5 @@ Maintain aspect ratio and scale down the video container
Could not find a proper tailwind css.
*/
.outer-max-width {
- max-width: 60%;
+ max-width: 70%;
}
diff --git a/web/src/routes/Event.jsx b/web/src/routes/Event.jsx
index 24d1b2349..19c9ee1f6 100644
--- a/web/src/routes/Event.jsx
+++ b/web/src/routes/Event.jsx
@@ -1,7 +1,9 @@
import { h, Fragment } from 'preact';
import { useCallback, useState, useEffect, useRef } from 'preact/hooks';
+import Link from '../components/Link';
import ActivityIndicator from '../components/ActivityIndicator';
import Button from '../components/Button';
+import ArrowDown from '../icons/ArrowDropdown';
import Clip from '../icons/Clip';
import Close from '../icons/Close';
import Delete from '../icons/Delete';
@@ -9,16 +11,17 @@ import Snapshot from '../icons/Snapshot';
import Dialog from '../components/Dialog';
import Heading from '../components/Heading';
import VideoPlayer from '../components/VideoPlayer';
+import { Table, Thead, Tbody, Th, Tr, Td } from '../components/Table';
import { FetchStatus, useApiHost, useEvent, useDelete } from '../api';
export default function Event({ eventId, close, scrollRef }) {
const apiHost = useApiHost();
const { data, status } = useEvent(eventId);
const [showDialog, setShowDialog] = useState(false);
+ const [showDetails, setShowDetails] = useState(false);
const [shouldScroll, setShouldScroll] = useState(true);
const [deleteStatus, setDeleteStatus] = useState(FetchStatus.NONE);
const setDeleteEvent = useDelete();
- const eventRef = useRef(null);
useEffect(() => {
// Scroll event into view when component has been mounted.
@@ -54,9 +57,10 @@ export default function Event({ eventId, close, scrollRef }) {
if (status !== FetchStatus.LOADED) {
return ;
}
-
+ const startime = new Date(data.start_time * 1000);
+ const endtime = new Date(data.end_time * 1000);
return (
-
+
@@ -92,13 +100,46 @@ export default function Event({ eventId, close, scrollRef }) {
/>
) : null}
+
+ {showDetails ? (
+
+
+ | Key |
+ Value |
+
+
+
+ | Camera |
+
+ {data.camera}
+ |
+
+
+ | Timeframe |
+
+ {startime.toLocaleString()} – {endtime.toLocaleString()}
+ |
+
+
+ | Score |
+ {(data.top_score * 100).toFixed(2)}% |
+
+
+ | Zones |
+ {data.zones.join(', ')} |
+
+
+
+ ) : null}
+
-
+
{data.has_clip ? (
Clip
new URLSearchParams(searchString), [searchString]);
+ const innerRef = useOuterClick(() => {
+ setViewEvent(null);
+ });
+
const viewEventHandler = useCallback(
(id) => {
//Toggle event view
@@ -39,8 +44,9 @@ const EventsRow = memo(
const start = new Date(parseInt(startTime * 1000, 10));
const end = new Date(parseInt(endTime * 1000, 10));
console.log('tablerow has been rendered');
+
return (
-
+
(scrollToRef[id] = el)}
width="150"
height="150"
className="cursor-pointer"
@@ -102,12 +107,12 @@ const EventsRow = memo(
|
{viewEvent === id ? (
- |
+ | (scrollToRef[id] = el)}>
setViewEvent(null)} scrollRef={scrollToRef} />
|
) : null}
-
+
);
}
);
diff --git a/web/src/routes/Events/hooks/useClickOutside.jsx b/web/src/routes/Events/hooks/useClickOutside.jsx
new file mode 100644
index 000000000..d0e5d133c
--- /dev/null
+++ b/web/src/routes/Events/hooks/useClickOutside.jsx
@@ -0,0 +1,21 @@
+import { useCallback, useEffect, useRef, useState } from 'preact/hooks';
+
+export const useOuterClick = (callback) => {
+ const callbackRef = useRef(); // initialize mutable ref, which stores callback
+ const innerRef = useRef(); // returned to client, who marks "border" element
+
+ // update cb on each render, so second useEffect has access to current value
+ useEffect(() => {
+ callbackRef.current = callback;
+ });
+
+ useEffect(() => {
+ document.addEventListener('click', handleClick);
+ return () => document.removeEventListener('click', handleClick);
+ function handleClick(e) {
+ if (innerRef.current && callbackRef.current && !innerRef.current.contains(e.target)) callbackRef.current(e);
+ }
+ }, []); // no dependencies -> stable click listener
+
+ return innerRef; // convenience for client (doesn't need to init ref himself)
+};
diff --git a/web/src/routes/Events/index.jsx b/web/src/routes/Events/index.jsx
index 85f7b1e99..22e677144 100644
--- a/web/src/routes/Events/index.jsx
+++ b/web/src/routes/Events/index.jsx
@@ -4,7 +4,7 @@ import Heading from '../../components/Heading';
import { TableHead, Filters, TableRow } from './components';
import { route } from 'preact-router';
import { FetchStatus, useApiHost, useEvents } from '../../api';
-import { Table, Tbody, Tfoot, Tr, Td } from '../../components/Table';
+import { Table, Tfoot, Tr, Td } from '../../components/Table';
import { useCallback, useEffect, useMemo, useReducer } from 'preact/hooks';
import { reducer, initialState } from './reducer';
import { useSearchString } from './hooks/useSearchString';
@@ -89,12 +89,12 @@ export default function Events({ path: pathname, limit = API_LIMIT } = {}) {
-
- {events.map((props, idx) => {
- const lastRowRef = idx === events.length - 1 ? lastCellRef : undefined;
- return ;
- })}
-
+
+ {events.map((props, idx) => {
+ const lastRowRef = idx === events.length - 1 ? lastCellRef : undefined;
+ return ;
+ })}
+
|
|