The app icon was a flat .icns, so it did not follow the Dark, Clear and
Tinted icon styles of macOS 26. Add an Icon Composer icon with the tile
as the background fill and the logomark as an unlit layer. Dark mode
gets a dark tile and the lighter purple mark, and Clear and Tinted get a
heavier mono mark.
The bundle gets the compiled asset catalog when actool is from Xcode 26
or later. Earlier macOS versions and older toolchains keep the flat
app_icon.icns.
This fixes#11827.
Wait for load before the existing animation-frame sequence so fetching
and decoding finish before the repaint test runs. Keep its four frames
and completion behavior unchanged.
Image IDs belong to the resource storage of one context. Keep resolved
image filters in its raster cache so another context cannot reuse them.
Drop cached filters when their image resources are replaced or removed.
Ignore nonpositive and nonfinite intervals, and durations outside the
u64 microsecond range, before converting scheduler accounting values.
Preserve truncation for ordinary fractional durations without changing
clocks or scheduling.
Universal registrations can survive an initial-value descriptor
containing a valid variable reference because the descriptor is
discarded. Preserve statically named var() references as an invalid
effective initial value until a later valid descriptor replaces it.
Reuse the variable argument parser to preserve malformed-reference
handling and leave other substitution function kinds on their existing
descriptor path.
The registration syntax parser accepts escaped data type names because
it reads decoded identifier tokens. Reject escapes in those literal
names while retaining normal identifier parsing for custom identifiers.
An explicitly empty initial-value descriptor is treated as invalid
instead of an empty registered value. Accept the optional empty
declaration value and preserve it through universal-syntax parsing.
The declaration parser rejects an initial-value descriptor containing
both a function and a curly block. Preserve those arbitrary component
values in property descriptors so universal registrations retain their
complete initial value.
Descriptor value-type grammars bypass the metadata restriction on CSS-
wide keywords. Apply that restriction before trying each grammar so
invalid registration initial values are rejected consistently.
A queued fetch response can cancel a readable request body. This
creates promise reactions, which need incumbent callback settings.
Prepare those settings alongside the existing execution context.
Add an HTTP POST authentication challenge regression, with GET and
successful POST controls.
Computed style enumeration omits custom properties, including registered
initial values. Enumerate the effective custom names, omit
guaranteed-invalid values and cache the result across repeated indexed
reads.
Header-change: Cache computed custom property names per declaration.
Computed registered lists are returned as a single opaque value. Use the
matching registration syntax to split multiplied values into iterations
while preserving a transform list as one transform value.
Specified custom properties currently accept typed objects that the
Typed OM setter must reject. Enforce unparsed values and CSS-wide
keywords at the shared setter boundary, and remove the obsolete subclass
exceptions.
Appending no values currently replaces the existing declaration and
triggers a style-attribute callback. Return after validating the
property and existing value so an empty append leaves the declaration
unchanged.
Replacing a declaration through Typed OM exposes an intermediate style
attribute with that declaration removed. Combine removal and insertion
in the declaration update so observers receive one mutation with the
correct old and new values.
Expose keys, values, entries and forEach on style maps. Snapshot each
traversal to match existing engines, while refreshing cached property
names when declarations or registrations change.
Include @property registrations in computed map membership and preserve
computed property ordering. Cover registration changes, snapshots and
value retention across garbage collection in a native test.
Header-change: Expose effective registration traversal to style maps.
Cover registration names from stylesheets and the JavaScript API,
stylesheet changes, Unicode ordering and disconnected elements during
computed style-map iteration.
Typed OM currently accepts percentage objects for shape-image-threshold.
Restrict those typed assignments to numbers, matching Chrome and Safari
even though the current CSS Shapes grammar also permits percentages.
Typed numeric calculations are rejected by integer-valued properties.
Accept those calculations. The complete grammar check still rejects
them for compound grammars such as counters, and valid values reach
the existing rounding and range handling.
Zero is incorrectly reified as a pixel length for properties that accept
both lengths and numbers. Keep the number unit when the property's
grammar accepts a numeric value.
Component type checks accept bare numeric values for properties that
also require a name or tag. Validate typed numeric assignments against
the complete property grammar before replacing the declaration, keeping
the original internal value for valid assignments.
Update the existing Typed OM tests for counters, cursors and font tags.
Trailing whitespace after a postfix span is mistaken for an extra
grid-placement operand. Discard that whitespace before checking whether
the span ends the placement.
Typed OM rejects flex units for implicit grid tracks even though the
grid parser and layout representation support them. Accept nonnegative
flex literals through the existing grid representation and preserve the
rejection of flex calculations.
Computed relative colors retain their origin and channel keywords after
their inputs are resolved. Resolve available channels during
computation, keeping unknown currentcolor references until the element
color is available. Reuse the existing computed-form conversion to
preserve relative-color serialization and precision.
Direct sibling-counting functions are rejected by the color channel
parser's numeric path. Parse them as numeric channel inputs and use the
existing computation context to resolve their values.
On macOS, Qt lays out a push button by a native button rect that is
smaller than the widget, leaving room for a focus ring. The Reload
button's style sheet draws the button over the whole widget, so its
bottom edge stuck out past its column and was cut off. Lay the button
out by its widget rect, as the other styled buttons in the UI do.
A site whose only page in a process was an embedded frame showed the
favicon of the tab embedding it, so the task manager listed Google's
sign-in frame under the Reddit icon. A frame's page now has no favicon,
and the task manager shows its generic site icon instead.
The task manager labeled a page's process with its host, but a request
server with its site, so www.reddit.com and its request server showed
up as two sites, www.reddit.com and reddit.com. Pages and request
servers are both isolated by site, so label every process with the
registrable domain of its URL, and fall back to the host where there is
none, as for localhost or an IP address.
On macOS, the task manager's content fills the window's title bar, so
presses there reach our title bar widget and AppKit never moves the
window. Dragging the empty part of the title bar now starts an AppKit
window drag, as in the browser window, and double-clicking it zooms
the window.
The task manager lists a helper process with the process it works for,
but only image decoders recorded which process that was. MediaServer,
AudioServer, VideoDecoderServer and WebWorker processes had no owner,
so they appeared among the browser's own processes. An image decoder of
a worker did too, since its owner, the worker, had no site.
These servers now record the WebContent or WebWorker process they were
launched for, and a worker records the process that started it and the
site of its origin. The task manager follows owners up to the process
with a site, so a shared worker whose creator is gone stays with its
site.
Unwinding a deep recursion that catches the stack overflow exits JIT
code in every frame. Before each exit noted its frame, the code looked
for each frame it remembered among all live frames, one stack walk per
frame. The hCaptcha check on the claude.ai login measures the stack
depth this way, which never finished, so logging in failed.
The remembered frames are now a map keyed by frame id, and returned
ones are forgotten in one stack walk once they doubled since the last
time. Ids are never reused, so a later frame at the same address no
longer inherits the fruitless loop check budget of a returned one.
Before running the VM, we check that the pattern's required literal
occurs in the rest of the input. For ASCII input, that search used
iter().position(), which tests one byte per iteration.
Lexers that match anchored patterns like /^\n/ against the remaining
source pay for this scan on every token. Using memchr takes the
JetStream OfflineAssembler benchmark from 2.21s to 0.87s.
parseInt() accumulated digits in a double, which rounds at every step
once the value no longer fits in 53 bits. This made 20-digit inputs
like "18446462598732840000" come out one ulp off, which broke the
validation of the JetStream OfflineAssembler benchmark. The spec
requires exact results for radix 10 and power-of-two radices.
Parse long decimal digit runs as a whole, and accumulate power-of-two
radix digits exactly in a u64 with a sticky bit so they round once.
Preserve named font families as strings and record whether their names
can be emitted without quotes. This keeps spaces between identifier
tokens instead of escaping them as part of one identifier, while
preserving quotes for names that cannot round-trip unquoted.
Match Chrome and Firefox's family serialization, including quoted input
whose name is a valid identifier sequence. Keep other CSS strings and
custom identifiers unchanged.
Exercise quoted and unquoted family names through specified and computed
style, including names that need quotation and ordinary custom
identifiers with escaped spaces.
Resolve absolute keywords through the common table for default sizes
from 9px through 16px, and use a 1.2 ratio for relative keywords. Select
the table before scaling, including monospace font-size recascades,
and keep editing conversions consistent with computed styles.
Update font-size animation and keyword WPT expectations, together with
the layout and style checks affected by the corrected sizes.
Containment overrides were applied after projecting content sizes into
an orthogonal parent's axes. Apply them in the box's own frame before
projection, and avoid using its contained inline size as the parent's
inline size when the two axes differ.
Update the imported containment test and focused writing-mode coverage.
Import the intrinsic size override test and exercise horizontal and
vertical children in both horizontal and vertical parents. Record the
dimensions before fixing containment across an orthogonal context.
When resolving flexible lengths, step 5c only distributes free space if
it is non-zero. If a shrinking item froze at its max size and left zero
remaining free space, the other unfrozen items kept the target sizes
they were shrunk to in the previous iteration instead of going back to
their flex base size.
This squeezed the table of contents on ghostty.org docs pages down to a
sliver, breaking every word apart. Unfrozen items now take their flex
base size when there is no free space to distribute. This fixes three
subtests in css-flexbox/multiline-min-max.html.
A shrinking flex item keeps the size it was shrunk to after a sibling
freezes at its max size, even though the line has room for it again.
This test captures the current wrong layout.
Document hit testing skipped text fragments and only retargeted elements
from internal shadow trees. Resolve text hits to their DOM parent
element or shadow host and retarget against the querying document or
shadow root, sharing the algorithms and deduplicating after retargeting.
Expose elementFromPoint and elementsFromPoint on ShadowRoot for
compatibility, and update the imported and native hit-testing coverage.
Header-change: The generated ShadowRoot bindings call the new member
functions, and Document and ShadowRoot share the hit-testing helpers
declared next to the other DocumentOrShadowRoot algorithms.
Record current results for document and shadow root hit testing across
text, assigned elements, fallback slots, and nested shadow trees before
sharing the implementation and exposing the shadow root methods.
Malformed integrity expressions such as "-" or "-?" split into no
tokens, and indexing the empty token list aborted metadata parsing.
Find the first separators without creating temporary token lists, and
ignore malformed digests using CSP's base64-value grammar, as Firefox
does. Chromium also ignores empty digests and characters outside the
base64 and base64url alphabets, but does not validate padding.
Extend the fetch integrity coverage with incomplete expressions and
malformed hashes mixed with valid metadata.
Hidden contents require used size, layout, style, and paint containment.
Include those flags when building box values and invalidate the box
group when content-visibility changes, without changing the computed
contain property. This lets explicit intrinsic sizes apply to hidden
contents, and hidden elements now establish an independent formatting
context and a stacking context, as the updated layout tests show.
Update imported coverage and focused tests for visibility toggles and
intrinsic-size changes.
This makes five subtests of the upstream WPT test
css/css-sizing/contain-intrinsic-size/auto-007.html fail. They passed
only because hidden replaced elements were not size contained. With
containment applied, their "auto" intrinsic sizes need the last
remembered size, which we do not implement yet, so they use the
fallback length instead.
Import coverage comparing hidden contents with size containment, and add
focused coverage for hiding and showing an element while changing its
explicit intrinsic size. Record the current dimensions before fixing the
used containment flags.
Opening or closing a tab shows the buttons of every tab before they are
laid out again. The layout then hid the close buttons of inactive tabs
with set_revealed(false), but because they were visible, they faded out
from full opacity, so they all flashed for a moment.
A close button that was never revealed now hides at once.
Replaced elements retained their natural inline size and aspect ratio
under inline-size containment. Override the contained natural dimension
with its explicit intrinsic inner size, or zero, and remove the natural
aspect ratio while preserving the other dimension.
Apply the override when layout reads the replaced content facts, after
zoom and after an <svg> root negotiates its natural size, since the
explicit intrinsic inner size is already a zoomed computed length.
Reuse the same containment applicability check for layout nodes.
Cover intrinsic size overrides for ordinary and replaced elements with
inline-size containment in horizontal and vertical writing modes.
Add focused coverage for an <svg> root with a natural aspect ratio,
for zoomed replaced elements, and for changing the explicit intrinsic
inner size.
The guidelines describe how the browser chrome, its menus and panels,
and the browser's own pages look, move and read: platforms, metrics,
type, color tokens, shape and elevation, icons, components, motion,
keyboard, writing and accessibility.
The chrome is drawn from one set of color tokens and a line icon set,
in light, dark and a violet-dark for private windows, with a quieter
inactive window. The tab strip and the toolbar are laid out anew: the
Ladybird button opens the browser's menu, the address field holds the
site settings, zoom and bookmark buttons, downloads get a button of
their own, and the find bar, page dialogs, permission prompts and all
other panels are popovers that cast soft shadows.
Tabs open, close, move and change selection with short animations,
toolbar icons react to clicks, and nothing moves while the system asks
for less motion. Tabs can be listed and searched, recently closed ones
reopened, and those left open by a crash restored from a card over the
page. The sidebar, the Task Manager, the website issue report and the
window controls on Linux follow the same look, and dragging a tab out
on Wayland moves a window with it.
The app icon is a soft lavender-grey tile with a hairline edge, and
the logomark in Ladybird purple at about 60% of its width, with no
shine and no shadow on the mark. The 32 and 16 pixel icons are flat,
with a heavier line. The Linux window icon is the flat tile with a
darker bottom edge, and the private window icon is a dark violet tile
with a lilac mark.
The browser's own pages share new colors, controls and focus rings
from ladybird.css, in light and dark. Settings has a sidebar of
sections with a search field, picks the theme and where tabs go from
picture cards, chooses the search engine from a list, and lists the
filter lists and the sites content blocking is turned off on.
The welcome page asks for a search engine, where tabs go and content
blocking in one column. History, bookmarks, downloads, the About and
version pages and the error page are laid out to match.
Settings gain a theme for the browser's own interface, apart from the
one websites are asked to use, and the browser's own pages follow it.
The session store lists recently closed tabs and windows, reopens any
of them, and keeps the tabs a run left open when it quit unexpectedly,
for the browser to offer back. New tabs open blank, and the omnibox
offers to choose a search engine for a query when there is none.
Blocked requests are kept per page, for the site settings popover
to list. Menus, download statuses and the downloads button's state are
worded and counted for the new toolbar and popovers, the settings page
can turn content blocking back on for a site, and error pages stay
out of history.
The top-level viewport is square again: the corner radius the chrome
sent to WebContent, and the clips the compositor and the scrollbars
drew from it, are gone. The compositor's Picture-in-Picture controls
and the media placeholder are restyled.
A blocked request now reports its URL and what kind of resource it
was, so the browser can list what was blocked on a page. The error
page names the host and port it could not reach, and a document
that becomes active with a title reports that title.
A WebContent process's snapshot now lists the tabs whose pages it
hosts, each with its title and page, and counts the frames of other
tabs' pages it hosts, so that the Task Manager can show them.
Capture a traced owner of the refcounted font-face state in its display
timer callback. The timer can outlive the state when its other owners
disappear.
Reuse the existing loading owner to keep the state and its GC edges
alive until the timer stops. The resulting GC cycle can then be
collected.
Prepare sizing keywords and calc-size values for additive composition
using the same basis compatibility rules as interpolation. Add the
calculations directly while retaining zero lengths needed by sizing
serialization, so intrinsic sizes keep the underlying contribution.
Update the imported width, height, and min/max composition results.
Cover width, height, and their min/max variants when additive animation
endpoints combine lengths with intrinsic sizing keywords. Record the
current results before extending calc-size composition.
Run the final MessagePort collection check through gcAsync(), so that
collection runs in a deferred LibCore task with a small native stack.
The previous synchronous gc() ran inside the JavaScript timer callback,
where conservative roots could keep an otherwise unreachable port alive.
Keep the WeakRef assertion, wrapper expando, started-port liveness
check, and transport thread checks unchanged.
The seeked event can fire before the compositor presents the new frame.
Wait for the presented frame count to advance before requesting the next
video frame callback, instead of waiting for a fixed number of rAFs.
Keep the seek without a pending video frame callback so the test still
checks that callbacks do not receive frames presented before the
request.
Generated endpoint keyframes must use the current underlying value
with replacement composition. Preserve their implicit status through
preparation so earlier effects are included and additive composition
does not count the underlying value twice.
Update registered-property, logical-size, and stacked-transform WPT
expectations.
Cover an implicit final transform endpoint above another animated
transform, including reference-box-dependent values. Record the
current result before sampling implicit endpoints from the effect stack.
Cover scalar and list values for registered numeric, length, color,
angle, percentage, time, and resolution properties. Record the current
results for implicit keyframes before correcting additive composition.
Positions retain edge wrappers after their keywords resolve, while
explicit coordinate pairs use plain values. Drop those wrappers when
computing shape points so equivalent origin control points interpolate
and compare consistently without relaxing command anchor matching.
Make converted path coordinates use the same representation, and
update the existing control-point interpolation WPT expectations.
The spec's host-part matching returns "Does Not Match" for any host
that is not a domain, so a source like http://127.0.0.1:8000 blocked
every resource on that address. Chromium, Firefox and WebKit all match
the pattern against the URL's host string regardless of its type, and
sites rely on this, e.g. the Freenet gateway serving its apps with
default-src http://127.0.0.1:7509.
Match IPv4 and IPv6 hosts against their serialization as well, the way
those engines do. This also makes "*" and "*." wildcard patterns apply
to IP hosts. Opaque and empty hosts still never match.
Fixes#13256.
Normal is normalized to oblique zero degrees for interpolation, but
that normalization must not change the endpoints of a discrete switch
to or from italic. Fall back to the original property values when the
normalized font-style keywords differ. Update the discrete animation
and system-font WPT results.
Cover normal and italic endpoints, easing at the discrete switch, and
font shorthand animation to system fonts. Record the current results
before correcting how normalized font styles fall back to discrete.
Rust rounds negative half-values away from zero, while CSS requires
rounding them toward positive infinity. Interpolate in double precision
to preserve integer endpoints, then round and apply the property range.
Update the imported order and z-index WPT expectations.
Column flex containers used the incoming available height for line
breaking after resolving their automatic height and its constraints.
Use the resolved main size so wrapping, growth and content alignment
operate on the same column lines.
Keep the incoming space during intrinsic inline sizing and for
calc-size(auto, ...), which retains indefinite space for line breaking.
Update WPT expectations for wrapping, growth and content alignment.
Extrapolated contain-intrinsic-size animations can produce negative
dimensions because the longhands lack numeric range metadata. Declare
their nonnegative length ranges so existing animation range clamping
applies to width and height, including values paired with auto.
Update the imported interpolation WPT expectations.
WasmCoremark: 17925 -> 19763 (+10.3%)
A branch whose taken edge needed moves jumped to a stub that made
them and jumped again. For a br_if back to a loop header, that is
two taken jumps per iteration. We now invert such a branch: the exit
jumps out, and the back edge moves inline and jumps to the header.
URL style values were treated as unchanged during computation, so
getComputedStyle exposed relative URLs for properties such as fill and
stroke. Resolve url() values against their stylesheet or document base
URL during computation, including paint URLs with fallback colors, and
record that these values depend on the base URL. Empty URLs and local
fragment references keep their specified value.
The CONFIGURE_DEPENDS glob made every ninja invocation re-check the
iconset directory first. Name the ten iconset images explicitly so the
build no longer needs a glob verification step.
Mouse pointer moves report no button transition as button -1. Update
the two owned pointerover and pointermove rows to match the native
MouseButton::None path.
Manual rendering controls outlive a document. If a fixture times out
before restoring them, the next test in its view cannot receive
rendering opportunities.
Reuse the acknowledged pre-test history reset to restore automatic
rendering and the process render clock before loading the next fixture.
Keep navigation within a test under its existing clock.
Add a same-process harness regression for normal completion and a
timeout, with an automatic-rendering control.
Percentage block sizes can change a grid item's used inline size through
its aspect ratio even when its intrinsic contributions do not change.
Resolve those item sizes with the known rows before returning without
resizing the column tracks, and keep that basis for final alignment.
Update the WPT expectation for aspect-ratio grid item self alignment.
Expose Touch, TouchList and TouchEvent with immutable contact snapshots,
constructors, and trusted start, move, end and cancel delivery. Preserve
original touch targets through capture changes, removal and collection,
and retarget lists across shadow boundaries without changing snapshots.
Defer primary touch mouse fallback until touchend so cancellation can
suppress it, and suppress fallback for multi-touch gestures. The
delayed mouse events hit test the contact position, independently of
pointer capture, while click keeps the captured pointerup target. Track
the native mouse pointer separately from compatibility mouse and CSS
hover so touch hover can persist without moving the native pointer.
Keep desktop legacy touch feature detection separate from interface
exposure, including the legacy event factory. Add interface,
interaction, cancellation, capture, hover and lifetime coverage.
Header-change: Generated bindings need declarations of the new Touch
interfaces in the shared forward header. Document's hover setter no
longer takes the boundary event types that only its callers used.
Carry action contact and orientation properties through the shared
classic and BiDi action dispatcher. Track each contact independently,
assign primary pointers by type, and implicitly capture touch input.
Keep capture routed through local descendant frames after a contact
leaves their bounds, with other capture routing left explicit.
Separate pointer boundaries from the effective legacy mouse position so
primary touch and pen pointers can produce compatibility mouse events
and clicks without changing native mouse dispatch. A canceled primary
pen sends its compatibility mouseup to the window, and a primary pen
leaving the viewport clears its legacy mouse boundaries.
Add internals.performActions() so tests can run action sequences
through the UI input path, and route touch and pen testdriver actions
through it. A test that finishes from a listener waits until its
sequence completes. Add coverage for simultaneous contacts, action
properties, cancellation, hover exit, early completion and local
frames.
Header-change: EventHandler needs Document's boundary dispatch API to
separate primary pointer mouse transitions from native pointer hover.
Carry pointer identity, geometry, pressure, and orientation through the
existing input transport using generated IPC codecs. Keep native mouse
state inline and allocate additional pointer state only when needed.
Track capture and boundary targets by pointer ID for non-mouse input.
Exercise the transport through the UI process and verify that contacts
can hold independent capture targets without changing mouse dispatch.
WebDriver touch and pen actions remain disabled until capture routing
across navigables and compatibility mouse events are integrated.
Cover coordinate precision across pointer event types and consistent
exposure of the legacy touch handler attributes on Window, Document,
and elements. These tests provide controls for input dispatch changes.
Drive two named contacts through the UI input path and record their
pointer events, capture ownership, and geometry. Include native mouse
input after a pen sequence to cover isolation of the input state.
Grid item sizing used only the alignment position, so safe alignment
could place oversized items past the start of their grid area. Preserve
overflow modifiers on container defaults and use the logical start
fallback when an item's margin box exceeds its area.
Apply the fallback after size clamps while retaining auto margin
handling. Update WPT expectations and cover explicit and default
alignment in reversed axes.
Cover safe and unsafe align-items and justify-items behavior for grid
items that exceed their areas. Record the four failing subtests from
the WPT baseline before honoring overflow alignment.