Added
- An extension can open ANOTHER extension's panel.
ctx.tabs.openExtensionTab({ extensionId })andopenExtensionPanetake the id of whoever owns the panel, defaulting to your own, which is how an extension hands the user off to a tool that does the next step better than it could: Dev Environment knows the connection details for the database it is running, SQL Explorer knows how to browse one, and before this there was no route between them except telling the user to go and find it. It moves no data and reads nothing - the panel is rendered by the extension that owns it, exactly as if the user had opened it - so it stays ontabs:open, the permission for putting a tab on screen, and needs no new grant. It returnsnullwhen that extension is not installed, not enabled, or has no renderer for the panel, rather than opening an empty frame named after something the user may not have. Being an option field it is invisible to an older host, so it ships withopenExtensionTab.extensionIdinHOST_FEATURES:ctx.has("openExtensionTab.extensionId")is the check, and an extension using it needs noengines.tedibump. See host.ts, tedi.d.ts.
Changed
- The running-turn indicator is coloured by the reasoning level the turn is running at. The pixel block that animates while the AI works was muted at every level and foil at
max, so the deepest setting was visible and the four below it were not - the picker saidhighin amber and the thing that ran said nothing. Both indicators, the chat's status row and the status-bar pill, now take the level's own ink from the same table the picker reads,Autostaying muted because that is what the picker shows for it too. One table and one hook inlib/effort.tsrather than a colour map per surface, since a picker and an indicator that disagree about whathighlooks like are worse than neither being coloured. See effort.ts, ReasoningDropdown.tsx. - The block is a 2x4 strip, not a 4x4 square. Both places that draw it sit on one line of text - the status pill is 24px tall including its border, the chat's running row is a single 11.5px line - and a 22px square touched both edges of each. A strip is 10px, the height the 12px glyphs in the pill's other states occupy, so the running state finally sits on the same baseline as the rest. The diagonal chase follows the new geometry on its own: the wave now crosses four steps instead of six and reads as a head travelling left to right rather than corner to corner. The
rows/colsprops went with it, because both call sites want the same strip and a knob with one setting is a knob to keep in sync for nothing. See pixel-activity.tsx.
Fixed
- The
maxfoil in the pixel block was a flat cyan, not a foil..tedi-foilleaves its two repeating gradient layers atbackground-size: auto, which resolves to the element's own box - on a 4px cell that is a 4px tile, so the layer repeats every 4px and the per-cell--fxoffset that is supposed to make eight cells sample ONE continuous sheet wrapped inside a single period instead. Every cell drew the same crop. The block sat beside a picker rendering the wordmaxas a full cyan-violet-pink prism and claimed in its own comments to be cut from that same sheet. The layers are now sized to the block, so a cell is genuinely a window onto it and the hue run crosses the strip exactly as it crosses the word. See globals.css, pixel-activity.tsx. - A status-bar tooltip's calendar ran its last month label off the popover. Month labels are absolutely positioned on the column pitch and are wider than the column they name, which is fine everywhere except the end: the last month labels one of the final columns, so
Sepstarted 5px from the grid's right edge and finished flush against the popover's border, clipped mid-word during the open animation. The overhang now stops at the grid's right edge.100%inside atranslateis the element's own width, so the clamp costs no guess at how wide a month name is in the user's locale. Reported on AI Usage 0.1.12, whose year heatmap is the first grid wide enough to hit it. See ExtensionStatusItems.tsx.
macOS users: if Gatekeeper says TEDI "can't be opened because Apple cannot check it for malicious software" or "is damaged and can't be opened", drag the app to /Applications and run this once in Terminal:
xattr -cr /Applications/TEDI.app