Reputation: 1
I'm building a frontend interface for my anime API, so I used FetchApiDataService to fetch the anime list. I arranged all the anime in cards, and my idea was to implement a "carousel" due to the large number of anime. I set it up to show 5 cards at a time, with the remaining cards appearing when the user scrolls (using mouse or finger) or clicks the buttons to the left or right.
<!-- anime-card.component.html -->
<div class="container">
<button (click)="showPrevCard()">Prev</button>
<div class="card-carousel"
*ngFor="let anime of visibleAnimes; let i = index"
[ngClass]="{'main-card': i === 2, 'big-card': i === 1 || i === 3, 'small-card': i === 0 || i === 4}"
(mousedown)="startDrag($event)"
(touchstart)="startDrag($event)"
(mousemove)="onDrag($event)"
(touchmove)="onDrag($event)"
(mouseup)="endDrag()"
(touchend)="endDrag()">
<mat-card class="poster">
<img [src]="anime.ImagePath" [alt]="anime.Title" />
<mat-card-header>
<mat-card-title>{{ anime.Title }}</mat-card-title>
<mat-card-subtitle>The Manga writers is: {{ anime.MangaArtist?.Name }}</mat-card-subtitle>
<mat-card-content>
<div class="tags">
<span *ngFor="let genre of anime.Genre.Name; let i = index"
[ngStyle]="{'background-color': getGenreColor(i)}">{{ genre }}</span>
</div>
<div class="btn">
<a [routerLink]="['/animes', anime.Title]">Description</a>
</div>
</mat-card-content>
</mat-card-header>
</mat-card>
</div>
<button (click)="showNextCard()">Next</button>
</div>
// anime-card.component.ts
import { Component, OnInit, ChangeDetectorRef, HostListener } from '@angular/core';
import { FetchApiDataService } from '../fetch-api-data.service';
@Component({
selector: 'app-anime-card',
templateUrl: './anime-card.component.html',
styleUrls: ['./anime-card.component.scss']
})
export class AnimeCardComponent implements OnInit {
allAnimes: any[] = [];
visibleAnimes: any[] = [];
currentIndex = 0;
displayCount = 5;
centerIndex = 2;
private startX = 0;
private currentX = 0;
private isDragging = false;
constructor(
private fetchApiDataService: FetchApiDataService,
private cd: ChangeDetectorRef
) { }
ngOnInit(): void {
this.fetchApiDataService.getAllAnimes().subscribe((animes: any) => {
this.allAnimes = animes;
this.updateVisibleAnimes();
});
}
updateVisibleAnimes() {
this.visibleAnimes = [];
for (let i = 0; i < this.displayCount; i++) {
let anime = this.allAnimes[(this.currentIndex + i) % this.allAnimes.length];
let x = i - this.centerIndex;
let scale = this.calcScale(x);
let leftPos = this.calcPos(x, scale);
anime.transform = `translateX(${leftPos}%) scale(${scale})`;
this.visibleAnimes.push(anime);
}
this.cd.detectChanges();
}
calcPos(x: number, scale: number): number {
if (x < 0) {
return (scale * 100 - this.cardWidth(x, scale)) / 2;
} else if (x > 0) {
return 100 - (scale * 100 + this.cardWidth(x, scale)) / 2;
}
return 100 - (scale * 100 + this.cardWidth(x, scale)) / 2;
}
calcScale(x: number): number {
return 1 - 0.2 * Math.abs(x);
}
cardWidth(x: number, scale: number): number {
return scale * 200;
}
showNextCard() {
this.currentIndex = (this.currentIndex + 1) % this.allAnimes.length;
this.updateVisibleAnimes();
}
showPrevCard() {
this.currentIndex = (this.currentIndex - 1 + this.allAnimes.length) % this.allAnimes.length;
this.updateVisibleAnimes();
}
startDrag(event: MouseEvent | TouchEvent) {
this.isDragging = true;
this.startX = (event instanceof MouseEvent) ? event.pageX : event.touches[0].pageX;
}
onDrag(event: MouseEvent | TouchEvent) {
if (!this.isDragging) return;
this.currentX = (event instanceof MouseEvent) ? event.pageX : event.touches[0].pageX;
}
endDrag() {
if (!this.isDragging) return;
this.isDragging = false;
const diffX = this.currentX - this.startX;
if (diffX > 50) {
this.showPrevCard();
} else if (diffX < -50) {
this.showNextCard();
}
}
getGenreColor(index: number): string {
const colors = ['#03a8f5', '#ff5722', '#4CAF50', '#FFC107', '#9C27B0'];
return colors[index % colors.length];
}
}
However, the scrolling isn't working properly right now. The cards don't move instead, they change only after I release the mouse or lift my finger, so it doesn't give me the scrolling or swiping effect.
Upvotes: 0
Views: 98