- Listen for the viewer once ComfyUI is set up, so a viewer left open over a reload connects fully - A duplicated tab starts its own session instead of sharing the viewer - Ignore requests from a viewer that is not connected - Stop the render loop while the glass is hidden and the viewer shows no frames - Do not place the panel again on the 250 ms refresh - Build output URLs from filename, subfolder and type only - Viewer: skip undecodable frames, tolerate showPicker and blocked storage, keep the channel open on unload, shorten "Go to node…" Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
66 lines
2.8 KiB
TypeScript
66 lines
2.8 KiB
TypeScript
import { describe, it, expect, beforeEach, afterEach, vi } from 'vitest';
|
|
import { PopOutManager } from '../../src/magnify-glass/PopOutManager';
|
|
|
|
describe('Pop-out palette', () => {
|
|
let manager: PopOutManager;
|
|
let posted: any[];
|
|
|
|
beforeEach(() => {
|
|
vi.useFakeTimers();
|
|
posted = [];
|
|
vi.stubGlobal('app', { api: new EventTarget(), ui: {}, extensionManager: { workflow: { activeWorkflow: null } } });
|
|
vi.stubGlobal('BroadcastChannel', class {
|
|
onmessage: ((e: MessageEvent) => void) | null = null;
|
|
postMessage(message: unknown) { posted.push(message); }
|
|
close() { }
|
|
});
|
|
manager = new PopOutManager(() => ({ glass: 'on', inspector: true, reduceMotion: false, zoom: 300 }), () => { }, () => { });
|
|
manager.listen();
|
|
});
|
|
|
|
afterEach(() => {
|
|
manager.cleanup();
|
|
document.body.classList.remove('dark-theme');
|
|
document.body.removeAttribute('style');
|
|
vi.unstubAllGlobals();
|
|
vi.useRealTimers();
|
|
});
|
|
|
|
const pong = () => (manager as any).handleMessage({ type: 'pong' });
|
|
const palettes = () => posted.filter(m => m.type === 'config').map(m => m.data.palette);
|
|
|
|
it('sends the computed allowlisted properties, the scheme and the font, and resends only when they change', () => {
|
|
document.body.classList.add('dark-theme');
|
|
document.body.style.setProperty('--fg-color', '#dddddd');
|
|
document.body.style.setProperty('--comfy-menu-bg', '#202020');
|
|
document.body.style.setProperty('--not-allowlisted', 'red');
|
|
document.body.style.fontFamily = 'Inter, Arial, sans-serif';
|
|
pong();
|
|
pong();
|
|
expect(palettes()).toHaveLength(1);
|
|
const [palette] = palettes();
|
|
expect(palette.scheme).toBe('dark');
|
|
expect(palette.fontFamily).toBe('Inter, Arial, sans-serif');
|
|
expect(palette.properties['--fg-color']).toBe('#dddddd');
|
|
expect(palette.properties['--comfy-menu-bg']).toBe('#202020');
|
|
// Unset properties are sent empty, so the viewer drops an override that went away
|
|
expect(palette.properties['--mg-panel-accent']).toBe('');
|
|
expect(palette.properties).not.toHaveProperty('--not-allowlisted');
|
|
|
|
document.body.classList.remove('dark-theme');
|
|
document.body.style.setProperty('--mg-panel-accent', '#ff8800');
|
|
pong();
|
|
expect(palettes()).toHaveLength(2);
|
|
expect(palettes()[1].scheme).toBe('light');
|
|
expect(palettes()[1].properties['--mg-panel-accent']).toBe('#ff8800');
|
|
});
|
|
|
|
it('sends the palette again when the viewer reconnects', () => {
|
|
pong();
|
|
(manager as any).handleMessage({ type: 'close' });
|
|
pong();
|
|
expect(palettes()).toHaveLength(2);
|
|
expect(palettes()[1]).toEqual(palettes()[0]);
|
|
});
|
|
});
|