Skip to content

Commit 2d26172

Browse files
committed
Allow links & visits to specify their view transition direction, and apply it appropriately when navigating the history stack
A link may now set a attribute with forward or backward to specify the direction of its view transition. When using Turbo.visit, this behavior is controller by the existing option.
1 parent 9e057f2 commit 2d26172

File tree

3 files changed

+27
-3
lines changed

3 files changed

+27
-3
lines changed

src/core/drive/history.js

+19-2
Original file line numberDiff line numberDiff line change
@@ -87,8 +87,13 @@ export class History {
8787
this.location = new URL(window.location.href)
8888
const { restorationIdentifier, restorationIndex } = turbo
8989
this.restorationIdentifier = restorationIdentifier
90-
const direction = restorationIndex > this.currentIndex ? "forward" : "back"
91-
this.delegate.historyPoppedToLocationWithRestorationIdentifierAndDirection(this.location, restorationIdentifier, direction)
90+
const direction = this.restorationVisitDirection(restorationIdentifier, restorationIndex)
91+
92+
this.delegate.historyPoppedToLocationWithRestorationIdentifierAndDirection(
93+
this.location,
94+
restorationIdentifier,
95+
direction
96+
)
9297
this.currentIndex = restorationIndex
9398
}
9499
}
@@ -109,4 +114,16 @@ export class History {
109114
pageIsLoaded() {
110115
return this.pageLoaded || document.readyState == "complete"
111116
}
117+
118+
restorationVisitDirection(restorationIdentifier, restorationIndex) {
119+
const historyDirection = restorationIndex > this.currentIndex ? "forward" : "back"
120+
const originalVisitDirection =
121+
this.restorationData[restorationIdentifier]?.direction === "back" ? "back" : "forward"
122+
123+
return historyDirection === "forward" ? originalVisitDirection : this.oppositeDirection(originalVisitDirection)
124+
}
125+
126+
oppositeDirection(direction) {
127+
return direction === "forward" ? "back" : "forward"
128+
}
112129
}

src/core/index.js

+2
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,8 @@ export function registerAdapter(adapter) {
3434
* @param options Options to apply
3535
* @param options.action Type of history navigation to apply ("restore",
3636
* "replace" or "advance")
37+
* @param options.direction Logical direction of the navigation, applies to
38+
* view transitions ("forward", "back")
3739
* @param options.historyChanged Specifies whether the browser history has
3840
* already been changed for this visit or not
3941
* @param options.referrer Specifies the referrer of this visit such that

src/core/session.js

+6-1
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,10 @@ export class Session {
9595
visit(location, options = {}) {
9696
const frameElement = options.frame ? document.getElementById(options.frame) : null
9797

98+
if (["forward", "back"].includes(options.direction)) {
99+
this.history.updateRestorationData({ direction: options.direction })
100+
}
101+
98102
if (frameElement instanceof FrameElement) {
99103
const action = options.action || getVisitAction(frameElement)
100104

@@ -250,8 +254,9 @@ export class Session {
250254
followedLinkToLocation(link, location) {
251255
const action = this.getActionForLink(link)
252256
const acceptsStreamResponse = link.hasAttribute("data-turbo-stream")
257+
const direction = link.getAttribute("data-turbo-visit-direction")
253258

254-
this.visit(location.href, { action, acceptsStreamResponse })
259+
this.visit(location.href, { action, acceptsStreamResponse, direction })
255260
}
256261

257262
// Navigator delegate

0 commit comments

Comments
 (0)