Read the original article:How to implement a text carousel card (or text slideshow card)?
Problem Description
When implementing the text carousel card functionality, how can I ensure that the text pauses scrolling when it reaches the boundary of the control, and synchronously waits for other text carousel animations to finish, in order to achieve coordinated control between the animations?
Background Knowledge
- Scroll: A scrollable container component. When the layout size of the child component exceeds the size of the parent component, the content can be scrolled.
- Scroller: The controller for a scrollable container component. This component can be bound to a container component, and then used to control the scrolling of the container component.
Solution
By controlling the 'Scroll' component's movement with 'Scroller' and adding animation effects, you can achieve a text carousel effect similar to a marquee. Simultaneously, set a timer to realize automatic scrolling, and use the 'Scroller's 'isAtEnd' method to monitor the scroll status and determine if the component has scrolled to the bottom, thereby ascertaining whether the text has been fully displayed.
Reference code is as follows:
import { myMarqueeCard } from './myMarqueeCard'
// Entry Component
@Entry
@Component
struct Index {
@State textList: string[] = [
'this is a test string1 this is a test string1 this is a test string1.',
'this is a test string2 this is a test string2.',
'this is a test string3 this is a test string3 this is a test string3 this is a test string3.',
]
build() {
Row() {
Column() {
myMarqueeCard({
textList: this.textList,
})
}
.width('100%')
}
.height('100%')
}
}
// Custom Marquee Effect
@Component
export struct myMarqueeCard {
@Prop textList: string[]
scroller1: Scroller = new Scroller()
scroller2: Scroller = new Scroller()
scroller3: Scroller = new Scroller()
build() {
Column() {
this.SingleText(this.textList[0], this.scroller1)
this.SingleText(this.textList[1], this.scroller2)
this.SingleText(this.textList[2], this.scroller3)
}
}
@Builder
SingleText(text: string, scroller: Scroller) {
Scroll(scroller) {
Row() {
Text(text).fontSize(30)
}
}
.width(300)
.scrollable(ScrollDirection.Horizontal)
.enableScrollInteraction(false)
.scrollBar(BarState.Off)
.onAppear(() => {
this.handleScroll(scroller)
})
}
handleScroll(scroller: Scroller) {
let timer: number = setInterval(() => {
const curOffset: OffsetResult = scroller.currentOffset()
scroller.scrollTo({
xOffset: curOffset.xOffset + 50, yOffset: curOffset.yOffset, animation: {
duration: 1000,
curve: Curve.Linear
}
})
if (scroller.isAtEnd()) {
clearInterval(timer);
if (this.scroller1.isAtEnd() && this.scroller2.isAtEnd() && this.scroller3.isAtEnd()) {
this.scroller1.scrollTo({xOffset: 0, yOffset: 0, animation: { duration: 0 }})
this.scroller2.scrollTo({xOffset: 0, yOffset: 0, animation: { duration: 0 }})
this.scroller3.scrollTo({xOffset: 0, yOffset: 0, animation: { duration: 0 }})
}
}
}, 500)
}
}

Top comments (0)