Texture fills show in the vector tab as soon as they load (#196)
After signing out and back in, a texture fill stayed in its base colour until something else redrew the vector tab. The texture library is a singleton that outlives the editor. Four widgets subscribed to it and never unsubscribed. After a new sign-in the first loaded texture called a destroyed canvas, which threw and stopped the loop before the vector tab heard about the image. - TextureCanvas, TileCanvas, ShaderPreview and WorldViewport now unsubscribe in destroy(). This is the pattern FontPreview and VectorArtCanvas already use. WorldViewport leaves both the texture and the font library. - FileLibrary.notifyChange catches errors per listener. A broken listener no longer starves the others. The error is still logged as "[textures] a listener failed". - e2e 47i no longer forces a redraw. It waits up to 3 s for the tab to show the texture on its own. Findings: - The trigger was e2e module 45 (sign out, sign in), not the texture fill. My note in #196 that the browser showed no exception was wrong. The counter-check shows it clearly. Tests: - ./check.sh: 137 files, 2051 tests, exit 0 (before 136 / 2049) - 2 new unit tests in tests/viewport/file-library.test.ts - GM_STEPS=45,47 after a fresh seed: ALL PASSED, 71 checks - Counter-check with the old source and the new check: 1 FAIL (shape stays #0000ff) plus the TypeError. Old FileLibrary.ts fails the first unit test. - No full e2e run locally. The check count is unchanged. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
This commit is contained in:
1 parent
66d6aafbb4
commit
6a2b06dd4b
7 files changed
+114
-14
No files matched your search
@@ -68,6 +68,7 @@ export class TileCanvas extends Widget {
|
||||
private board = { w: 0, h: 0 };
|
||||
private info: TileInfo | null = null;
|
||||
private needsFit = true;
|
||||
private readonly stopPictures: () => void;
|
||||
|
||||
constructor(private readonly state: EditorState) {
|
||||
super();
|
||||
@@ -90,7 +91,13 @@ export class TileCanvas extends Widget {
|
||||
state.on('project', () => this.redraw());
|
||||
state.on('load', () => this.show(''));
|
||||
// A picture arrives asynchronously; the board is empty until it does.
|
||||
textureLibrary.onChange(() => this.redraw());
|
||||
this.stopPictures = textureLibrary.onChange(() => this.redraw());
|
||||
}
|
||||
|
||||
/** The library outlives a signed-out editor; a stale listener would redraw destroyed graphics. */
|
||||
override destroy(options?: Parameters<Widget['destroy']>[0]): void {
|
||||
this.stopPictures();
|
||||
super.destroy(options);
|
||||
}
|
||||
|
||||
override measure(): Size {
|
||||
|
||||
Reference in new issue
Block a user