Analyze Arousal Valence with MorphCast SDK v1.16
by morphcast
HTML
<input type="file" id="photo" accept="image/*">
<button id="analyze">Analyze Arousal/Valence</button>
<pre id="out"></pre>
<script src="https://ai-sdk.morphcast.com/v1.16/ai-sdk.js"></script>
<script>
// ---------- Helpers ----------
const outEl = document.getElementById('out');
const print = (obj) => outEl.textContent = typeof obj === 'string'
? obj
: JSON.stringify(obj, null, 2);
// Convert File -> ImageData (draw once on an offscreen canvas)
async function fileToImageData(file) {
const url = URL.createObjectURL(file);
try {
const img = new Image(); img.crossOrigin = 'anonymous';
await new Promise((ok, ko) => { img.onload = ok; img.onerror = ko; img.src = url; });
const c = document.createElement('canvas');
const ctx = c.getContext('2d', { willReadFrequently: true });
c.width = img.naturalWidth; c.height = img.naturalHeight;
ctx.drawImage(img, 0, 0);
return ctx.getImageData(0, 0, c.width, c.height);
} finally { URL.revokeObjectURL(url); }
}
// ---------- Custom single-frame source ----------
// Produces exactly one ImageData on demand via analyzeFrame(...)
let pending = null, resolver = null;
const photoSource = {
// Called by your app to push the next frame
analyzeFrame(imageData) {
if (resolver) { resolver(imageData); resolver = null; }
else { pending = imageData; }
},
// Called by the SDK to fetch a frame
getFrame() {
if (pending) { const p = Promise.resolve(pending); pending = null; return p; }
return new Promise(res => resolver = res);
},
start(){}, stop(){}, get stopped(){ return false; }
};
// ---------- SDK init (one-time) ----------
let startSdk, stopSdk, sdkReady = false;
(async () => {
const { start, stop } = await CY.loader()
.licenseKey("9087cfd2037a28a79769fdcaa4962252379cd2e2fd0b") // required if your license demands it
...