Skip to content

Commit

Permalink
update annotation types
Browse files Browse the repository at this point in the history
  • Loading branch information
SheepTester committed May 23, 2024
1 parent f12b005 commit 08a55ff
Show file tree
Hide file tree
Showing 3 changed files with 90 additions and 30 deletions.
38 changes: 17 additions & 21 deletions src/App.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import { PlayIcon } from './components/PlayIcon'
import { PauseIcon } from './components/PauseIcon'
import { Part, strategize } from './video-strategy'
import { useNow } from './useNow'
import { AnnotationContents } from './components/Annotation'

type PlayState =
| { playing: false; time: number }
Expand All @@ -22,17 +23,12 @@ export function App () {
{
id: -2,
type: 'annotation',
annotation: { type: 'set-layout', value: 'Lecturer Only' }
annotation: { type: 'set-layout', layout: 'avatar-only' }
},
{
id: -3,
type: 'annotation',
annotation: { type: 'animation', value: 'Show Name' }
},
{
id: -4,
type: 'annotation',
annotation: { type: 'set-background', value: 'Scripps Pier' }
annotation: { type: 'gesture', gesture: 'point', towards: 'top' }
},
{
id: -5,
Expand Down Expand Up @@ -64,7 +60,7 @@ export function App () {
<div className='editor'>
<div className='output'>
<div className='menubar'>
<strong className='logo'>Lecture Editor</strong>
<strong className='logo'>Ready Room</strong>
<button className='menubar-btn'>File</button>
<button className='menubar-btn'>Edit</button>
</div>
Expand Down Expand Up @@ -127,7 +123,10 @@ export function App () {
{
id: nextId.current++,
type: 'annotation',
annotation: { type: 'animation', value: 'hey' }
annotation: {
type: 'set-layout',
layout: 'slide-only'
}
}
)
)
Expand Down Expand Up @@ -163,16 +162,7 @@ export function App () {
parts[i - 1]?.type !== 'annotation' ? 'first' : ''
} ${parts[i + 1]?.type !== 'annotation' ? 'last' : ''}`}
>
<span>
{part.annotation.type === 'animation'
? 'Play animation'
: part.annotation.type === 'set-background'
? 'Change background to'
: part.annotation.type === 'set-layout'
? 'Change layout to'
: ''}{' '}
<strong>{part.annotation.value}</strong>
</span>
<AnnotationContents annotation={part.annotation} />
<button
className='remove-btn'
onClick={() => {
Expand Down Expand Up @@ -213,7 +203,10 @@ export function App () {
{
id: nextId.current++,
type: 'annotation',
annotation: { type: 'animation', value: 'hey' }
annotation: {
type: 'set-layout',
layout: 'slide-avatar'
}
},
{
id: nextId.current++,
Expand All @@ -224,7 +217,10 @@ export function App () {
: parts.toSpliced(i + 1, 0, {
id: nextId.current++,
type: 'annotation',
annotation: { type: 'animation', value: 'hey' }
annotation: {
type: 'set-layout',
layout: 'avatar-only'
}
})
)
}
Expand Down
52 changes: 52 additions & 0 deletions src/components/Annotation.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
import { Annotation, Gesture, GestureTarget, Layout } from '../video-strategy'

const layoutNames: Record<Layout, string> = {
'slide-only': 'slide with voiceover',
'slide-avatar': 'slide and avatar',
'avatar-only': 'avatar only'
}
const gestureNames: Record<Gesture, string> = {
point: 'Point',
nod: 'Nod',
glance: 'Glance'
}
const gestureTargetNames: Record<GestureTarget, string> = {
top: 'top of slide',
middle: 'middle of slide',
bottom: 'bottom of slide'
}

export type AnnotationContentsProps = {
annotation: Annotation
}
export function AnnotationContents ({ annotation }: AnnotationContentsProps) {
switch (annotation.type) {
case 'set-layout':
return (
<span>
Change layout to <strong>{layoutNames[annotation.layout]}</strong>
</span>
)
case 'gesture':
return (
<span>
<strong>{gestureNames[annotation.gesture]}</strong> towards{' '}
<strong>{gestureTargetNames[annotation.towards]}</strong>
</span>
)
case 'set-slide':
return (
<span>
Change slide to <strong>todo</strong>
</span>
)
case 'play-video':
return (
<span>
Play video <strong>todo</strong>
</span>
)
default:
return null
}
}
30 changes: 21 additions & 9 deletions src/video-strategy.ts
Original file line number Diff line number Diff line change
@@ -1,7 +1,16 @@
export type Layout = 'slide-only' | 'slide-avatar' | 'avatar-only'
export type Gesture = 'point' | 'nod' | 'glance'
export type GestureTarget = 'top' | 'middle' | 'bottom'
export type Annotation =
| { type: 'animation'; value: string }
| { type: 'set-layout'; value: string }
| { type: 'set-background'; value: string }
| { type: 'set-layout'; layout: Layout }
| { type: 'set-slide'; image: HTMLImageElement | null }
| {
type: 'play-video'
video: HTMLVideoElement | null
from: number
to: number
}
| { type: 'gesture'; gesture: Gesture; towards: GestureTarget }
export type PartBase =
| { type: 'text'; content: string }
| { type: 'annotation'; annotation: Annotation }
Expand All @@ -26,11 +35,11 @@ export function strategize (parts: PartBase[]): Stategy {
const actions: Action[] = []

let time = 0
let caption = ''
for (const part of parts) {
if (part.type === 'text') {
const lines = part.content.split(/\s*\n\s*/)
for (const line of lines) {
let caption = ''
let lastIndex = 0
for (const { index } of line.matchAll(/\s+/g)) {
// `index` is the index of the first whitespace character
Expand All @@ -54,16 +63,19 @@ export function strategize (parts: PartBase[]): Stategy {
} else {
caption += rest
}
if (caption.length > 0) {
const content = caption.trim()
captions.push({ content, time })
time += content.replace(/\s/g, '').length * EST_TIME_PER_CHAR
}
}
if (caption) {
caption += ' '
}
} else {
actions.push({ ...part.annotation, time })
}
}
if (caption.length > 0) {
const content = caption.trim()
captions.push({ content, time })
time += content.replace(/\s/g, '').length * EST_TIME_PER_CHAR
}

return { captions, actions, length: time }
}

0 comments on commit 08a55ff

Please sign in to comment.