@@ -91,36 +91,47 @@ public class AudioNavigator<S : Configurable.Settings, P : Configurable.Preferen
9191 .mapNotNull { it.duration }
9292 .takeIf { it.size == readingOrder.items.size }
9393 ?.sum()
94+
95+ val coercedOffset =
96+ playback.coerceOffset(currentItem.duration)
97+
9498 val totalProgression =
9599 if (itemStartPosition == null ) {
96100 null
97101 } else {
98- readingOrder.duration?.let { (itemStartPosition + playback.offset ) / it }
102+ readingOrder.duration?.let { (itemStartPosition + coercedOffset ) / it }
99103 }
100104
101105 val locator = requireNotNull(publication.locatorFromLink(link))
102106 locator.copyWithLocations(
103- fragments = listOf (" t=${playback.offset .inWholeSeconds} " ),
104- progression = item.duration?.let { playback.offset / it },
107+ fragments = listOf (" t=${coercedOffset .inWholeSeconds} " ),
108+ progression = item.duration?.let { coercedOffset / it },
105109 totalProgression = totalProgression
106110 )
107111 }
108112
109113 override val playback: StateFlow <Playback > =
110114 audioEngine.playback.mapStateIn(coroutineScope) { playback ->
115+ val itemDuration =
116+ readingOrder.items[playback.index].duration
117+
118+ val coercedOffset =
119+ playback.coerceOffset(itemDuration)
120+
111121 Playback (
112122 playback.state.toState(),
113123 playback.playWhenReady,
114124 playback.index,
115- playback.offset ,
125+ coercedOffset ,
116126 playback.buffered
117127 )
118128 }
119129
120130 override val location: StateFlow <Location > =
121131 audioEngine.playback.mapStateIn(coroutineScope) {
122132 val currentItem = readingOrder.items[it.index]
123- Location (currentItem.href, it.offset)
133+ val coercedOffset = it.coerceOffset(currentItem.duration)
134+ Location (currentItem.href, coercedOffset)
124135 }
125136
126137 override fun play () {
@@ -178,4 +189,11 @@ public class AudioNavigator<S : Configurable.Settings, P : Configurable.Preferen
178189 is AudioEngine .State .Buffering -> State .Buffering
179190 is AudioEngine .State .Failure -> State .Failure (error)
180191 }
192+
193+ private fun AudioEngine.Playback.coerceOffset (duration : Duration ? ): Duration =
194+ if (duration == null ) {
195+ offset
196+ } else {
197+ offset.coerceAtMost(duration)
198+ }
181199}
0 commit comments