FlowStudio è organizzato come una pipeline in tempo reale: ad ogni nuovo frame aggiorna il campo di moto, i segnali per-cella, le mappe di frequenza, gli spettri e (opzionalmente) l’oscillatore di regione (“blob”). La GUI imposta i parametri e visualizza i risultati; la catena di misura è la stessa sia con sorgente live (camera) sia con file video.
Sorgente (Camera / File video) ↓ frame @ FPS → dt = 1/FPS Preprocessing (opzionale: Blur / CLAHE) ↓ Optical Flow (frame t → t+1) [vedi §6] ↓ Affidabilità / Maschera (photoErr, FB, gradiente, MAD…) [vedi §7] ↓ Riduzione a griglia (aggregazione celle + EMA + stabilità) [vedi §8] ↓ Segnale per-cella x[n] (modulo / U / V) + decimazione D → fs_eff = FPS/D [vedi §9–§10] ↓ Rapid Oscillation Analyzer (passa-banda + autocorrelazione → f0, corr, rms, stable) [vedi §10] ↓ Mappe & Overlay (f0/corr/rms/stable → overlay a colori + mappe debug) [vedi §11] ↓ Diagnostica Entropia (H(t), mappa H_local, proxy Ṡ) [vedi §12] ↓ Aggregazione & decisioni ├─ Spettro / Waterfall (istogramma su celle attive) [vedi §13] ├─ Oscillatore blob (Hz(t), Coh(t) su celle stabili) [vedi §11.2] └─ Detector (baseline/cambi) → Event recorder → export CSV / riassunti Before–After [vedi §14–§18]
HH:MM:SS.mmm, si azzera su Start/Stop e quando apri/riavvii un file video.FlowStudio analizza una sequenza di immagini (camera o file video) per misurare micro-movimenti e, soprattutto, oscillazioni rapide (ad esempio tremore, vibrazioni, micromovimenti periodici) all’interno di una regione selezionata. L’idea chiave è:
FlowStudio produce sia informazioni visive (overlay, vettori, mappe, spettro/waterfall) sia numeriche (statistiche, eventi, riassunti Before/After).
Tra il frame t e il frame t+1 FlowStudio stima un vettore v(x,y) = (u, v) per ogni pixel (o un sottoinsieme denso), che significa “questo punto si è spostato di u pixel in orizzontale e v pixel in verticale”.
Se un punto si muove avanti–indietro in modo periodico, la sua componente di spostamento nel tempo assomiglia a un’onda. La frequenza è “quanti cicli al secondo” (Hz).
Un video è una sequenza di frame. Se l’acquisizione è a FPS frame al secondo, allora l’intervallo temporale tra due frame è:
dt = 1 / FPS (secondi)
Esempio: 200 FPS ⇒ dt = 0.005 s (5 ms).
Per misurare un’oscillazione di frequenza f devi campionare abbastanza velocemente. La regola base è il limite di Nyquist: serve circa FPS > 2·f. In pratica è meglio avere più margine (ad esempio 5×–10×) per una stima robusta.
Le grandezze interne sono in pixel per frame (px/frame). Per convertirle in unità fisiche devi fornire una calibrazione:
um_per_px = micrometri rappresentati da 1 pixel
Le velocità diventano:
velocita_um_s = (velocita_px_frame) * FPS * um_per_px
Nota: se non conosci la calibrazione puoi comunque confrontare valori relativi (prima/dopo, condizioni diverse), ma non puoi riportare µm/s in modo affidabile.
.sqlite con metriche per-frame e (se richiesto) vettori di flow su griglia. Vedi §15.5.| Comando | Significato |
|---|---|
| Start | Avvia l’elaborazione sulla sorgente selezionata (camera o file). |
| Stop | Ferma l’elaborazione e rilascia la sorgente. |
| Open Video… | Apre un file video. |
| Open Recent | Riapre uno degli ultimi file video usati (fino a 16). |
| Restart Video | Riavvia riproduzione/elaborazione dall’inizio del file corrente. |
| Pause / Resume | Mette in pausa/riprende l’elaborazione. Alla ripresa avviene una risincronizzazione. |
| Resync | Pulisce lo stato a breve termine e risincronizza la catena (utile dopo ROI/seek). |
| Reset | Reset completo degli stati interni e contatori (analisi, istogrammi, baseline del detector). |
| Clear ROI | Disabilita la ROI e torna al full-frame. |
| Fit docks | Ripristina la disposizione predefinita dei pannelli. |
| Select Camera... | Seleziona il dispositivo camera UVC/DirectShow (Windows). Utile con più camere collegate. |
| Camera Resolution... | Seleziona risoluzione/formato della camera. Consigliato prima di Start (soprattutto su USB2/USB3) per stabilizzare FPS e qualità. |
| Camera Settings... | Apre le proprietà del driver (pagine UVC/DirectShow, Windows). Serve per disattivare auto-esposizione/auto-gain quando possibile. |
| Video hardcopy | Registra l’intera finestra (menu + dock + status) in un file video. Utile per documentare sessioni e parametri “così come visti”. |
| Session recording (SQLite)... | Crea/aggiorna un file SQLite (.sqlite) con una riga per frame (tabella frames) e un record per ogni “run”/segmento (tabella runs). Consiglio: abilita la registrazione e poi Restart Video / Start camera per un take pulito. [vedi §15.5] |
| Record grid flow (heavy) | Se attivo, registra anche i vettori di flow per-cella (tabella grid_flow). Può aumentare molto carico e dimensione del DB: usa hop più alto e/o griglia meno densa. |
| Verify session DB integrity... | Esegue PRAGMA integrity_check e statistiche base sul file di sessione selezionato, stampando il risultato nel Log. Utile per confermare che la registrazione sia completa. |
| AI Request... | Crea un pacchetto (report + dati strutturati) per valutazione esterna: PDF/JSON/CSV/immagini. Non modifica l’analisi, è solo export. |
| Help | Apre questa guida. |
Le scorciatoie servono per tarare rapidamente durante l’osservazione:
La ROI è un rettangolo dell’immagine su cui viene eseguita l’analisi. Tutto (moto, frequenza, spettro) è calcolato solo dentro la ROI.
Cambiare ROI cambia geometria e buffer storici. Dopo modifiche alla ROI (o dopo uno spostamento/seek nel file), usa Resync per evitare di mescolare dati non compatibili.
FlowStudio stima lo spostamento tra frame consecutivi in scala di grigi. Il modello classico è la costanza di luminosità: un punto mantiene circa la stessa intensità mentre si muove.
Sia I(x,y,t) l’intensità. Se un punto si sposta di (u,v) tra due frame:
I(x, y, t) ≈ I(x + u, y + v, t + dt)
Un algoritmo di optical flow trova (u,v) che soddisfa al meglio questa relazione su intorni e su più scale. FlowStudio usa un metodo denso multi-scala adatto a moti piccoli/medi.
Non tutti i vettori di moto sono affidabili. FlowStudio calcola una maschera e una confidenza per evitare che zone inaffidabili contribuiscano alla stima di frequenza.
photoErr(x,y) = | I2(x,y) − warp(I1, flow12)(x,y) |Errore basso ⇒ il moto spiega bene i cambiamenti di intensità.
fbErr ≈ | flow12(p) + flow21(p + flow12(p)) |Errore alto ⇒ occlusioni, blur, mismatch.
Ogni indizio ha una soglia (Tphoto, Tfb, Tdev, Tgrad, Tmad). Un pixel passa la maschera se soddisfa i criteri abilitati. Dopo la maschera, una pulizia morfologica opzionale rimuove puntini isolati.
Una qualità globale semplice è la frazione di pixel/celle che passano i controlli di affidabilità. Nei riassunti viene riportata come quality (%).
Il flow denso produce un vettore per pixel. Analizzare la frequenza per pixel sarebbe troppo pesante e rumoroso. FlowStudio aggrega quindi i vettori in celle quadrate di lato Cell size.
Dentro ogni cella si usano solo i pixel affidabili (maschera). Il vettore di cella è una stima robusta:
Una cella è valida solo se contiene almeno Min samples pixel affidabili.
I vettori di cella oscillano per rumore. Una media mobile esponenziale (EMA) li smussa:
v_smooth[t] = α · v_new[t] + (1 − α) · v_smooth[t−1]
Il parametro Max jump limita cambi improvvisi non realistici: se |v_new − v_prev| è troppo grande l’aggiornamento viene respinto o limitato.
Per stimare oscillazioni servono celle con segnale coerente nel tempo. La persistenza mantiene un contatore stable per cella: cresce quando il moto cambia poco (entro epsilon) e cala quando diventa incoerente o mancante.
Dopo la griglia, hai un vettore per cella e per frame. Lo trasformi in un segnale 1D x[n]. FlowStudio offre tre modalità:
Perché usare una componente e non la magnitudine? Una componente con segno conserva la direzione (avanti–indietro diventa un’oscillazione pulita attorno a zero), mentre la magnitudine può “raddrizzare” il segnale e introdurre armoniche.
È il motore centrale della frequenza. Per ogni cella FlowStudio mantiene un buffer corto e stima la frequenza dominante.
Con FPS alti (es. 200 FPS) puoi decimare di un fattore D: si fa la media di D frame per ottenere un campione. Questo riduce rumore e costo computazionale.
fs_eff = FPS / D
Tutta la parte di frequenza usa fs_eff.
Il moto grezzo contiene drift lento (postura, drift camera) e rumore veloce. FlowStudio usa un passa-banda costruito con:
Sono filtri standard del 1° ordine in tempo discreto:
high-pass: y[n] = a · ( y[n−1] + x[n] − x[n−1] ) low-pass: y[n] = y[n−1] + b · ( x[n] − y[n−1] )
I tagli sono in Hz e vengono interpretati con fs_eff.
Ogni cella ha un buffer circolare di N campioni. La durata temporale coperta è:
durata_finestra = N / fs_eff (secondi)
L’analizzatore aggiorna ogni Hop campioni, quindi la velocità di aggiornamento è circa:
aggiornamenti_al_secondo ≈ fs_eff / Hop
N piccolo ⇒ risposta rapida ma risoluzione peggiore; N grande ⇒ stima più stabile ma più lenta.
Per trovare periodicità, FlowStudio calcola l’autocorrelazione normalizzata. Prima si sottrae la media (oscillazione centrata a zero). Poi, per ogni lag L:
corr(L) = Σ_{i=0..M−1} x[i]·x[i+L] / sqrt( Σ x[i]^2 · Σ x[i+L]^2 )
dove M = N − L
È un coefficiente di correlazione tra il segnale e una copia ritardata. È circa in [−1, +1]. FlowStudio usa il picco positivo come misura di periodicità.
La ricerca è limitata alla banda [fMin, fMax]. Le frequenze corrispondono a lag:
L ≈ fs_eff / f lagMin = floor(fs_eff / fMax) lagMax = ceil (fs_eff / fMin)
Si sceglie il lag con corr(L) massimo nell’intervallo [lagMin, lagMax].
Prima di fidarsi dei picchi corr, FlowStudio controlla che il segnale abbia energia sufficiente:
RMS = sqrt( mean( x[i]^2 ) )
Se RMS è sotto RMS thr, la cella è inattiva (nessuna oscillazione significativa).
Il lag è discreto, ma il periodo reale può stare tra due lag. FlowStudio raffina il lag migliore con una piccola interpolazione parabolica usando corr(L−1), corr(L), corr(L+1). Poi:
f0 = fs_eff / lagFrac
Anche dopo gating, la frequenza può saltare per rumore. FlowStudio mantiene un contatore per cella: se |f0 − f0_precedente| ≤ freqTol, il contatore aumenta; altrimenti riparte. Questo valore “stable” è un’ulteriore misura di affidabilità.
Dopo l’analisi di tutte le celle, FlowStudio costruisce mappe su griglia:
L’overlay fonde:
La trasparenza (alpha) deriva da corr, rms e stable, con le soglie principali:
se corr < CorrThr o rms < RmsThr → alpha = 0 cc = (corr − CorrThr) / (1 − CorrThr) limitato a [0,1] rr = (rms − RmsThr ) / (3·RmsThr) limitato a [0,1] ss = min(1, stable / stableNeed) alpha = alphaBase · cc · rr · ss · AlphaBoost limitato a [0,1]
La vista finale:
output = (1−alpha)·(BW·BWgain) + alpha·(COLOR·ColorGain)
Quindi: oscillazioni più forti, più periodiche e più stabili diventano più visibili.
Oltre alla frequenza per cella, FlowStudio può stimare anche un oscillatore equivalente dell’intera ROI/blob: una traccia unica Hz(t) più un numero di coerenza Coh(t) che indica quanto la regione si comporta come “un solo oscillatore” (coerenza alta) rispetto a una somma di parti sfasate/rumore (coerenza bassa).
Dove lo trovi nella GUI. Il grafico temporale è nella tab Oscillator Plot (tabificata insieme a Spettro/Waterfall e Log). Le immagini di debug sono nel dock F0 Map → sub-tab Oscillator (Amp/Phase/Contrib/Mask). Per risparmiare CPU, l’intero blocco resta spento se Enable blob oscillator (heavy) non è selezionato.
L’oscillatore del blob usa solo le celle già considerate affidabili dal Rapid Oscillation Analyzer. Per ogni cella i sono disponibili: corri (periodicità), rmsi (energia) e stablei (persistenza). L’insieme attivo è:
S = { i | corr_i ≥ CorrThr e rms_i ≥ RmsThr e stable_i ≥ stableNeed }
Se |S| è troppo piccolo, l’output dell’oscillatore viene marcato come non valido per quell’aggiornamento (mancano celle stabili sufficienti per una stima robusta).
Per ogni cella in S, FlowStudio mantiene già un segnale temporale passa-banda xi[n] (gli stessi filtri/decimazione usati dalla stima per cella; vedi Sezioni 10.1–10.3). Il segnale equivalente di regione è la media:
y[n] = (1 / |S|) · Σ_{i∈S} x_i[n]
Intuizione: la media riduce il rumore non correlato e mette in evidenza il moto comune alle celle stabili.
Ad ogni aggiornamento (ogni Hop campioni), FlowStudio calcola la trasformata discreta di Fourier (DFT) di y[n] sulla finestra corrente:
Y[k] = Σ_{n=0..N−1} y[n] · exp( −j · 2π · k · n / N )
f_k = k · fs_eff / N
Il bin di massimo viene cercato solo nella banda [fMin, fMax] (la stessa banda usata per f0 per cella):
kMin = ceil( fMin · N / fs_eff )
kMax = floor( fMax · N / fs_eff )
k* = argmax_{k ∈ [kMin..kMax]} |Y[k]|
Hz = f_{k*}
Amp = |Y[k*]| (ampiezza relativa)
Amp è una magnitudine spettrale relativa della regione. Se servono unità fisiche (µm/s, µm), va combinata con calibrazione (µm/px) e FPS.
Una volta noto il bin di picco k*, ogni cella stabile contribuisce con un coefficiente complesso a quella frequenza:
X_i = Σ_{n=0..N−1} x_i[n] · exp( −j · 2π · k* · n / N )
La coerenza è un rapporto di allineamento di fase (0..1):
Coh = | Σ_{i∈S} X_i | / Σ_{i∈S} |X_i|
Se è attivo Compute debug maps, FlowStudio costruisce mappe per cella alla frequenza di picco k*:
C_i = |X_i| · cos( φ_i − φ_ref ), con φ_ref = arg( Σ_{i∈S} X_i )
Così è immediato vedere chi è in fase (positivo) e chi in controfase (negativo).
La ricerca del picco usa una FFT/DFT sul segnale di regione y[n] per trovare il bin migliore k* nella banda [fMin, fMax]. Una volta noto k*, i coefficienti complessi per-cella Xi a quel solo bin possono essere calcolati in due modi equivalenti:
La DFT su un bin è:
X_i(k*) = Σ_{n=0..N−1} x_i[n] · exp( −j · ω · n ), con ω = 2π · k* / N
L’algoritmo di Goertzel calcola lo stesso valore tramite una ricorrenza del 2° ordine:
s[n] = x[n] + 2·cos(ω)·s[n−1] − s[n−2] con s[−1]=s[−2]=0 X(k*) = s[N−1] − exp(−j·ω)·s[N−2]
In FlowStudio la FFT su y[n] serve a scegliere k* (Hz). Lo stesso k* viene poi usato per calcolare Coh e (opzionalmente) le mappe debug tramite i coefficienti Xi sul singolo bin. La matematica è equivalente alla FFT completa, con costo CPU più basso.
Questo pannello aggiunge una famiglia di misure basate su entropia, pensate come diagnostica di quanto l’attività oscillatoria è concentrata oppure distribuita in frequenza e nello spazio. In FlowStudio “entropia” è usata nel senso di Shannon (entropia dell’informazione) applicata a distribuzioni costruite a partire dalle mappe già disponibili (f0, corr, rms, stable) e dall’istogramma di frequenza.
Ad ogni aggiornamento FlowStudio costruisce già un istogramma di frequenza contando quante celle hanno una frequenza dominante f0 valida (solo celle che passano gli stessi gate di “oscillazione valida”: banda + CorrThr + RmsThr + StableNeed). Sia l’istogramma composto da K bin e conteggi ck. Si normalizza in probabilità:
p_k = c_k / Σ c_k H = − Σ p_k · log(p_k) (entropia di Shannon; base e) H01 = H / log(K) (normalizzata in 0..1)
Mentre H(t) è un riassunto a livello di regione, Hlocal(x,y) è una mappa. Per ogni cella (x,y) FlowStudio considera un intorno quadrato di raggio R (in celle di griglia) e costruisce un piccolo istogramma dei valori f0 nell’intorno, dopo quantizzazione in K bin (parametro “bins”). Poi calcola l’entropia di Shannon (normalizzata 0..1) di quella distribuzione locale.
Formalmente, per un intorno N(x,y):
p_k(x,y) = conteggio celle in N(x,y) con f0 nel bin k / totale celle valide in N(x,y) H_local(x,y) = − Σ p_k(x,y) · log(p_k(x,y)) H_local01(x,y)= H_local(x,y) / log(K)
Una produzione entropica termodinamica, in prima approssimazione, sarebbe:
Ṡ ≈ P_diss / T
Tuttavia, dalle sole immagini spesso non hai accesso diretto alla potenza dissipata calibrata. FlowStudio fornisce quindi un proxy che correla con “quanta attività oscillatoria c’è” e che è visualizzabile come mappa. Un default pratico è:
powerProxy(x,y) = rms(x,y)^2 · corr(x,y) (solo su celle valide/gated) P_proxy(t) = Σ powerProxy(x,y) Sdot_proxy(t) = powerScale · P_proxy(t) / T
Note. rms è calcolato dopo passa-banda; corr è il picco di autocorrelazione. Il fattore powerScale è una scala utente per rendere leggibile il plot. Se disponi di un modello meccanico calibrato (massa, rigidezza, smorzamento) o una stima diretta di Pdiss, puoi sostituire il proxy con l’espressione fisica mantenendo identica la visualizzazione.
t_s, H01, Sdot.Metric Space è una vista 3D che trasforma l’andamento temporale di molte metriche (frequenze, entropia, qualità, trigger, ecc.) in una traiettoria nello spazio. Ogni punto della curva rappresenta un campione nel tempo (uno ogni Hop frames) e viene colorato secondo la metrica scelta. L’obiettivo non è “misurare una nuova grandezza”, ma vedere in un colpo d’occhio lo stato del sistema: regimi stabili, transizioni, cluster e differenze Before/After.
FlowStudio costruisce un vettore di caratteristiche a 16 dimensioni (normalizzato in modo robusto con mediana e MAD su una finestra temporale) che include, tra le altre, queste grandezze:
Quel vettore viene poi “compresso” in 3D con un embedding:
| Parametro | Cosa fa | Note pratiche |
|---|---|---|
| Enable | Attiva la generazione della traiettoria. | Se disattivo, la vista resta ferma. |
| Hop frames | Decimazione temporale: 1 punto ogni N frame. | Aumenta per alleggerire (es. 3–10). |
| Window (sec) | Finestra usata per normalizzazione robusta e (se non congelata) per aggiornare la PCA. | Più lunga = base più stabile, ma meno reattiva. |
| Embed | PCA oppure LMDS. | LMDS è più costoso; usa landmark moderati. |
| Freeze basis | Blocca normalizzazione + base quando c’è abbastanza storia. | Consigliato per confronti e per evitare “salti” geometrici. |
| View mode | Curva 3D o asse tempo (z=t), con resa: line/points, ribbon, tube, density. | Ribbon/tube aiutano la lettura; density mostra un “attrattore”. |
| Color | Colora i punti per Time, Peak Hz, Entropy H, Osc Hz, Quality, Global speed, Osc Coh. | Ottimo per capire “che cosa cambia” lungo la traiettoria. |
| Max points | Limite alla storia (numero massimo di punti mantenuti). | Evita crescita infinita; utile per sessioni lunghe. |
| Landmarks (LMDS) | Numero di landmark per LMDS. | 256 è spesso un buon compromesso. |
| Reset | Azzera la traiettoria e ricomincia. | Usalo dopo cambi di sorgente o di condizioni. |
In modalità Density cloud i punti vengono voxelizzati in una griglia 3D (bins^3) e mostrati come una nuvola pesata. L’overlay Iso disegna un’isorisuperficie delle zone più dense: è una specie di firma della traiettoria.
.mhd + .raw)
+ un file meta.json. Include tipicamente: densità normalizzata/raw, media dello scalar, modulo del gradiente.Ogni cella che passa il gating contribuisce a un bin dell’istogramma. Il bin rappresenta una frequenza, usando una scala:
bin = round( f0 · scale ) (scale = bin per Hz)
Si accumulano solo le frequenze in [Hist fMin, Hist fMax].
La cella può contribuire con un semplice conteggio o con un peso:
La pesatura enfatizza oscillazioni forti/periodiche e riduce quelle deboli/rumorose.
Il bin massimo definisce la frequenza dominante del frame:
peakHz = peakBin / scale
La waterfall è una visualizzazione tempo–frequenza: ogni riga è un istogramma, e le righe scorrono nel tempo. È utilissima per capire se la frequenza è stabile, deriva o è intermittente.
Il detector genera un trigger quando la frequenza dominante cambia oltre la variabilità normale. Mantiene una baseline (media mu e varianza var) con una media mobile esponenziale (EWMA).
mu[t] = (1−α)·mu[t−1] + α·f[t] var[t] = (1−α)·var[t−1] + α·(f[t]−mu[t])^2 sigma = sqrt(var)
α piccolo ⇒ memoria lunga (baseline lenta).
Un cambiamento è significativo se:
|f − mu| > max( absHz, rel·mu, kSigma·sigma )
Baseline e trigger si aggiornano solo quando il frame ha abbastanza celle valide. Così la baseline non viene “sporcata” da frame senza segnale.
Quando il detector triggera, l’event recorder salva sequenze di immagini attorno all’evento:
Al momento del trigger può salvare anche snapshot diagnostiche: overlay, mappa corr, mappa f0, maschera.
Oltre al salvataggio “a eventi” (Event recorder), FlowStudio può registrare una sessione di misura completa in un database SQLite.
Il file risultante (.sqlite) contiene metriche per-frame (QC) e, opzionalmente, i vettori di moto su griglia.
.sqlite. La voce rimane spuntata (registrazione “armata”).grid_flow).nome.sqlite-wal e nome.sqlite-shm. Durante la registrazione il file principale .sqlite
può restare relativamente piccolo: è normale. Allo stop FlowStudio esegue un checkpoint per “ripiegare” i dati nel file principale.
Se devi copiare la sessione mentre stai registrando, copia anche -wal e -shm insieme al .sqlite.
| Tabella | Contenuto |
|---|---|
meta | Chiavi/valori: schema, versione, data creazione, meta_json (JSON fornito dalla UI), source_meta_json (info sorgente). |
runs | Un record per segmento/run (inizio acquisizione o “restart”): contiene timestamp iniziale e snapshot dei parametri sorgente (fps, dimensioni, ecc.). |
frames | Una riga per frame con le principali metriche di QC: peak/baseline Hz, quality, activity, fps, drop, luminanza/blur/saturazione, ROI, ecc. |
grid_flow | (Opzionale) Vettori di flow su griglia: per ogni frame (eventualmente sottocampionato da hop) salva (cx,cy,u,v,conf,stable). |
events | Eventi leggeri (JSON): run_start/run_end, roi_changed, ed eventuali altri marker futuri. |
Per verificare rapidamente che il file sia sano e completo usa File → Verify session DB integrity...:
FlowStudio esegue PRAGMA integrity_check; e stampa nel Log anche conteggi e range di indici (runs/frames).
-- quante righe sono state scritte SELECT COUNT(*) FROM frames; -- frame per run SELECT run_id, COUNT(*) AS n FROM frames GROUP BY run_id ORDER BY run_id; -- intervallo temporale (microsecondi UTC) del run 1 SELECT MIN(t_us), MAX(t_us) FROM frames WHERE run_id=1; -- picco medio e qualità media (run 1) SELECT AVG(peak_hz) AS peakHz_mean, AVG(quality01) AS q_mean FROM frames WHERE run_id=1;
Esporta gli ultimi N campioni di:
Esporta gli ultimi N istogrammi riportando solo i bin non zero: ogni riga contiene tempo, frame, activeCount, weightSum, bin, Hz e count. È molto più leggero quando i bin sono tanti (es. 1024).
L’analisi Sonata è un riassunto “di sessione” del contenuto spettrale. Usa lo storico degli istogrammi per trovare le frequenze più presenti nel tempo.
Concettualmente:
Parametri:
Durante la registrazione, ogni frame contribuisce con:
Sia FPS_seg l’FPS misurato nel segmento. La conversione in µm/s è:
valore_um_s = valore_px_frame · FPS_seg · um_per_px
| Metrica | Significato |
|---|---|
| RMS speed (µm/s) | La velocità globale per frame è |globalMotion|. RMS speed è la root-mean-square di tale velocità, convertita in µm/s. Rappresenta l’intensità complessiva del moto. |
| Drift (µm/min) | Velocità globale media convertita in µm/min. Rappresenta drift lento o spostamento sostenuto. |
| Dominant frequency (Hz) | Media di peakHz sul segmento. È la frequenza tipica dell’oscillazione. |
| Frequency stability (Hz) | Deviazione standard di peakHz sul segmento. Più bassa ⇒ frequenza più stabile. |
| Peak amplitude (µm/s) | Usa bestRms (px/frame) della best cell convertito in µm/s. È un proxy della “forza/ampiezza” dell’oscillazione. |
| Peak/Band ratio | Media di peakToBand. Vicino a 1 ⇒ un’unica frequenza domina (picco stretto). Più basso ⇒ spettro più largo / frequenze miste. |
| Events/min | Quante volte il detector di cambiamento di frequenza ha triggerato nel segmento, normalizzato al minuto. |
| Micro-activity (µm/s) | Media del moto residuo dopo aver rimosso la traslazione globale della ROI. Misura micromovimento locale “interno” più che drift dell’intera ROI. |
| Active area (%) | Frazione di campioni residui sopra una soglia (~0.5 px/frame), media sul segmento, in percentuale. |
| Quality (%) | Media dell’inlier ratio (quota di moto affidabile) in percentuale. Qualità bassa ⇒ misura probabilmente non interpretabile. |
Oltre al detector principale, FlowStudio caratterizza periodi “jerk-like” usando statistiche della velocità globale: stima media e deviazione standard “running”, poi apre un evento quando la velocità supera media + 3·std, e lo chiude quando resta sotto media + 2·std per alcuni frame (isteresi).
Da questi eventi ricava:
Durante la registrazione FlowStudio misura anche:
Viene generato un flag semplice:
Coh è una metrica di allineamento di fase:
Coh = | Σ_{i∈S} X_i | / Σ_{i∈S} |X_i| (0..1)
| Acronimo / termine | Significato in FlowStudio |
|---|---|
| ROI | Regione di Interesse: rettangolo in cui gira l’analisi (fuori ROI viene ignorato). |
| FPS | Frame per secondo (frequenza di campionamento del flusso video). |
| dt | Intervallo tra frame: dt = 1/FPS. |
| Nyquist | Regola di campionamento: la frequenza massima misurabile è circa FPS/2 (meglio avere margine nella pratica). |
| Optical flow | Stima dello spostamento tra frame consecutivi; produce un vettore (u,v) per pixel o per regione. |
| (u,v) | Componenti orizzontale/verticale dello spostamento, tipicamente in px/frame. |
| px/frame | Pixel per frame: unità interna del moto (prima della conversione in unità fisiche). |
| um_per_px | Calibrazione: micrometri per pixel (µm/px). Permette unità fisiche (µm, µm/s). |
| Maschera / inlier | Insieme di pixel/celle affidabili che passano i controlli e contribuiscono alle stime. |
| photoErr | Errore fotometrico dopo warp; basso ⇒ il flow spiega bene i cambiamenti d’intensità. |
| FB / fbErr | Errore di coerenza forward–backward; alto ⇒ occlusioni/blur/mismatch. |
| MAD | Median Absolute Deviation: misura robusta della dispersione usata per stabilità/outlier a livello di cella. |
| EMA | Exponential Moving Average: smussamento temporale dei vettori/segnali di cella. |
| Decimazione (D) | Media di D frame/campioni consecutivi per ridurre rumore e costo CPU. |
| fs_eff | Frequenza di campionamento effettiva dopo decimazione: fs_eff = FPS/D. |
| N | Lunghezza finestra (numero di campioni) usata per stimare la frequenza. |
| Hop | Passo di aggiornamento (in campioni) tra analisi successive della finestra. |
| Banda [fMin,fMax] | Intervallo di ricerca in frequenza (Hz) usato dall’analizzatore (e, opzionalmente, da altri blocchi). |
| HP / LP | Filtri passa-alto / passa-basso usati per costruire un passa-banda (tagli: hpCut / lpCut). |
| RMS | Root Mean Square: energia del segnale filtrato (gate di attività/energia). |
| Corr / corr(L) | Picco di autocorrelazione normalizzata; “score di periodicità” (gate e trasparenza alpha). |
| CorrThr | Soglia di correlazione: periodicità minima per accettare una cella. |
| f0 | Frequenza dominante per-cella (Hz). 0 = “non valida”. |
| stable / stableNeed | Contatore di persistenza e relativa soglia: per quanto tempo la cella mantiene f0 coerente. |
| Celle attive | Celle che passano i gate corr/rms/stable nell’update corrente e contribuiscono a mappe/istogrammi. |
| Spettro / istogramma | Distribuzione delle frequenze per-cella nella ROI (eventualmente pesata con corr/rms). |
| Waterfall | Storico nel tempo degli spettri; utile per vedere drift, burst e cambi di banda. |
| Oscillatore blob | Stima “a livello ROI”: produce Hz(t) e Coh(t) sull’insieme di celle stabili. |
| Hz(t) | Traccia della frequenza dominante di regione (un valore per update) dall’oscillatore blob. |
| Coh | Coerenza (0..1): rapporto di allineamento di fase tra celle stabili; alta ⇒ “tipo oscillatore unico”. |
| DFT / FFT | Trasformata discreta di Fourier / versione veloce (FFT) usate per cercare picchi in spettro. |
| Goertzel | DFT efficiente su un singolo bin (quando serve una sola frequenza). |
| UVC | USB Video Class (interfaccia standard per camere USB su Windows). |
| BW gain / Color gain / Alpha boost | Guadagni di visualizzazione: luminosità B/N, saturazione colore e forza della trasparenza overlay. |
| quality (%) | Rapporto globale di inlier (frazione di pixel/celle affidabili), indicatore rapido della “salute” dell’acquisizione. |
Fine documento.
Questa appendice chiarisce un equivoco molto comune: il formato in uscita dalla camera (cosa trasmette il dispositivo UVC su USB) non è lo stesso del formato del file (cosa salvi su disco). Le camere UVC tipicamente trasmettono:
Quando registri su disco scegli di solito un contenitore (es. MP4 o AVI) e un codec (es. H.264 o MJPG). L’applicazione (tramite OpenCV / backend multimediali del sistema) codifica i frame in ingresso nel codec scelto.
UVC (USB Video Class) è uno standard che permette alle camere di esporre stream video con un insieme di formati e risoluzioni supportati. Famiglie tipiche:
“YUV” (più correttamente Y′CbCr) descrive l’organizzazione dei pixel (come sono memorizzati luma e croma), non un contenitore file. MP4 è un contenitore che trasporta tipicamente stream compressi (H.264/H.265/AV1). In generale non si memorizza YUY2 “grezzo” dentro MP4. La catena tipica è:
Camera UVC esce in YUY2 (frame grezzi) → applicazione converte in BGR/grigio → encoder comprime in H.264 → file MP4
Oppure, se la camera esce in MJPG:
Camera UVC esce in MJPG (frame compressi) → decoder in BGR/grigio → (opzionale) ricodifica → file MP4/AVI
| Contenitore | Codec comuni | Note |
|---|---|---|
| MP4 | H.264 (AVC), H.265 (HEVC), AV1 | Molto efficiente; a bitrate basso può introdurre artefatti; attenzione a sorgenti a framerate variabile (VFR). |
| AVI | MJPG, XVID/DivX, non compresso | Semplice e compatibile; ottimo per MJPG; il file cresce molto se non compresso. |
| MKV | H.264/H.265, VP9, AV1 | Contenitore flessibile; dipende dal supporto del backend. |
I codec effettivamente disponibili dipendono dal backend OS (Windows Media Foundation / DirectShow) e dalla build di OpenCV.
FlowStudio usa il modello tipico di QMainWindow (Qt): la finestra è composta da una vista centrale e da vari dock widget (pannelli agganciabili) attorno. Se non hai familiarità con Qt, questa appendice spiega come far ricomparire, spostare e ridimensionare i pannelli.