Skip to content

Add animate parameter to splitPane to skip entry animation#25

Open
shouryamaanjain wants to merge 3 commits intomanaflow-ai:mainfrom
shouryamaanjain:fix/split-restore-animation
Open

Add animate parameter to splitPane to skip entry animation#25
shouryamaanjain wants to merge 3 commits intomanaflow-ai:mainfrom
shouryamaanjain:fix/split-restore-animation

Conversation

@shouryamaanjain
Copy link

@shouryamaanjain shouryamaanjain commented Mar 14, 2026

Companion to manaflow-ai/cmux#1433fixes manaflow-ai/cmux#1376

Summary

  • add animate: Bool = true parameter to splitPane(_:orientation:withTab:insertFirst:) and its internal implementation
  • when false, SplitState is created with animationOrigin: nil so the entry animation is skipped
  • default behavior unchanged for all existing callers

Summary by CodeRabbit

Release Notes

  • New Features
    • Splitting panes with tabs now includes optional animation control—panes can slide in smoothly (default) or appear instantly.
    • Added callback handler for tab closure requests, enabling custom logic when users close tabs.

austinywang and others added 2 commits March 13, 2026 12:43
Allows the host application to distinguish user-initiated tab closes
(clicking the X button) from internal/programmatic closes, so it can
decide whether closing the last surface should also close the workspace.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
When restoring session state, splits should be created without entry
animation so that the saved divider positions are applied immediately
rather than being overridden by the animation code which forces 0.5.
Copy link

@greptile-apps greptile-apps bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Your free trial has ended. If you'd like to continue receiving code reviews, you can add a payment method here.

@coderabbitai
Copy link

coderabbitai bot commented Mar 14, 2026

📝 Walkthrough

Walkthrough

Adds an optional animate flag to the split-by-tab API (propagated through recursive split logic) and introduces a public onTabCloseRequest callback invoked when the UI requests a tab close.

Changes

Cohort / File(s) Summary
Split-by-Tab & recursion
Sources/Bonsplit/Internal/Controllers/SplitViewController.swift
Added animate: Bool = true to public splitPaneWithTab and to internal splitNodeWithTabRecursively; animation origin is set only when animate is true and the flag is propagated through recursive calls.
Tab close UI hook
Sources/Bonsplit/Internal/Views/TabBarView.swift
Calls optional onTabCloseRequest?(TabID(id: tab.id), pane.id) immediately when a tab close is requested from the UI, before performing the close.
Public API surface
Sources/Bonsplit/Public/BonsplitController.swift
Exposed public callback onTabCloseRequest: ((_ tabId: TabID, _ paneId: PaneID) -> Void)? and added animate: Bool = true parameter to splitPane(... withTab: ...), forwarded to internal controller.

Sequence Diagram(s)

mermaid
sequenceDiagram
participant UI as TabBarView
participant Public as BonsplitController
participant Internal as SplitViewController
participant Node as SplitNode
UI->>Public: close tab request (tabId, paneId)
Public->>Public: invoke onTabCloseRequest?(tabId, paneId)
Public->>Internal: request tab close (tabId, paneId)
Internal->>Node: perform closeTab

mermaid
sequenceDiagram
participant Caller as Client
participant Public as BonsplitController
participant Internal as SplitViewController
participant Node as SplitNode
Caller->>Public: splitPane(withTab, orientation, insertFirst, animate)
Public->>Internal: splitPaneWithTab(..., animate)
Internal->>Node: splitNodeWithTabRecursively(..., animate)
alt animate == true
Node->>Node: set animationOrigin (.fromFirst/.fromSecond)
else animate == false
Node->>Node: animationOrigin = nil
end
Node->>Node: recurse into child nodes (propagate animate)

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~20 minutes

Possibly related PRs

Poem

🐰 I nudged a pane and set it to glide,
Or held it still when you asked for no slide,
A quiet tap asks "may I go?" — a gentle plea,
I whisper back the callback — now set them free,
Hopping through panes, small changes with glee. 🥕

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 60.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately describes the main change: adding an animate parameter to splitPane to control entry animation behavior.
Linked Issues check ✅ Passed The PR successfully implements the technical requirements for issue #1376 by adding the animate parameter to prevent entry animations from overriding restored divider positions.
Out of Scope Changes check ✅ Passed All changes are directly scoped to implementing the animate parameter feature across the split pane API and internal controller logic as intended for issue #1376.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
📝 Coding Plan
  • Generate coding plan for human review comments

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link

@cubic-dev-ai cubic-dev-ai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

No issues found across 3 files

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🧹 Nitpick comments (1)
Sources/Bonsplit/Public/BonsplitController.swift (1)

54-57: Clarify callback contract for onTabCloseRequest.

Consider documenting that this hook is a request signal and can fire even if the subsequent close is vetoed, so consumers don’t treat it as a guaranteed close event.

✍️ Suggested doc update
 /// Called when the user explicitly requests to close a tab from the tab strip UI.
 /// Internal host-driven closes should not use this hook.
+/// Note: this is a request notification and may fire even if the close is later vetoed.
 `@ObservationIgnored` public var onTabCloseRequest: ((_ tabId: TabID, _ paneId: PaneID) -> Void)?
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@Sources/Bonsplit/Public/BonsplitController.swift` around lines 54 - 57,
Update the doc comment for the onTabCloseRequest property to state clearly that
this is a user-initiated "request" signal and not a guaranteed close event:
mention that handlers receive (tabId: TabID, paneId: PaneID), that the close can
be vetoed by the host or other logic, and consumers must not assume the tab is
closed after this callback fires (they should observe actual close events/state
changes instead); modify the comment on the `@ObservationIgnored` public var
onTabCloseRequest to include that clarification and any guidance about
side-effects or asynchronous veto handling.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@Sources/Bonsplit/Public/BonsplitController.swift`:
- Around line 423-425: Add documentation for the new animate parameter in the
public API comment for the BonsplitController method that takes insertFirst:
Bool, animate: Bool = true -> PaneID?; update the method's docblock to include a
brief `@param` (or similar) entry for animate describing that true performs the
restore with animation, false restores without animation, and that the default
is true so callers can opt out of animation when needed. Ensure the doc text
uses the parameter name animate and mentions the method returns a PaneID? so
callers can understand restore/no-animation behavior without reading
implementation.

---

Nitpick comments:
In `@Sources/Bonsplit/Public/BonsplitController.swift`:
- Around line 54-57: Update the doc comment for the onTabCloseRequest property
to state clearly that this is a user-initiated "request" signal and not a
guaranteed close event: mention that handlers receive (tabId: TabID, paneId:
PaneID), that the close can be vetoed by the host or other logic, and consumers
must not assume the tab is closed after this callback fires (they should observe
actual close events/state changes instead); modify the comment on the
`@ObservationIgnored` public var onTabCloseRequest to include that clarification
and any guidance about side-effects or asynchronous veto handling.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 4d8e0431-5b46-4f57-a9cc-a124c3ac231b

📥 Commits

Reviewing files that changed from the base of the PR and between 505181f and a216ccd.

📒 Files selected for processing (3)
  • Sources/Bonsplit/Internal/Controllers/SplitViewController.swift
  • Sources/Bonsplit/Internal/Views/TabBarView.swift
  • Sources/Bonsplit/Public/BonsplitController.swift

Copy link

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

🧹 Nitpick comments (1)
Sources/Bonsplit/Public/BonsplitController.swift (1)

518-523: API inconsistency: movingTab variant lacks animate parameter.

The splitPane(_:orientation:withTab:insertFirst:animate:) variant exposes animation control via the animate parameter, but the splitPane(_:orientation:movingTab:insertFirst:) variant does not, and will always use the default animate: true from the internal call.

This is likely intentional—the movingTab variant is used for drag operations where animation is expected—but the API is asymmetric. If future use cases (e.g., session restore) require non-animated moves, this variant would need the same animate parameter for consistency.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@Sources/Bonsplit/Public/BonsplitController.swift` around lines 518 - 523, The
movingTab variant splitPane(_:orientation:movingTab:insertFirst:) is missing the
animate parameter and always uses the default animate:true; modify the API to
accept an animate: Bool (defaulting to true for backward compatibility) on
splitPane(_:orientation:movingTab:insertFirst:animate:) and forward that value
to internalController.splitPaneWithTab(..., insertFirst: insertFirst, animate:
animate); also update any callers of
splitPane(_:orientation:movingTab:insertFirst:) to pass the animate flag where
appropriate or rely on the default.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Nitpick comments:
In `@Sources/Bonsplit/Public/BonsplitController.swift`:
- Around line 518-523: The movingTab variant
splitPane(_:orientation:movingTab:insertFirst:) is missing the animate parameter
and always uses the default animate:true; modify the API to accept an animate:
Bool (defaulting to true for backward compatibility) on
splitPane(_:orientation:movingTab:insertFirst:animate:) and forward that value
to internalController.splitPaneWithTab(..., insertFirst: insertFirst, animate:
animate); also update any callers of
splitPane(_:orientation:movingTab:insertFirst:) to pass the animate flag where
appropriate or rely on the default.

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 6a068090-1192-4d29-a2cf-119c3b5502e8

📥 Commits

Reviewing files that changed from the base of the PR and between a216ccd and f454880.

📒 Files selected for processing (1)
  • Sources/Bonsplit/Public/BonsplitController.swift

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

App does not remember my split size configuration

2 participants