@groupix/groupix-spinner
Version:
A lightweight Angular spinner library with customizable ball count, size, speed, and loading text
56 lines • 9.91 kB
JavaScript
import { Component, Input } from '@angular/core';
import * as i0 from "@angular/core";
import * as i1 from "@angular/common";
export class GroupixSpinnerComponent {
ballCount = 3;
size = 'l';
balls = [];
sizeClass = 'ball-l';
ngOnInit() {
this.updateBallCount();
this.updateSizeClass();
}
ngOnChanges() {
this.updateBallCount();
this.updateSizeClass();
}
updateBallCount() {
const count = Math.min(Math.max(this.ballCount, 3), 9);
this.balls = Array.from({ length: count }, (_, i) => i);
}
updateSizeClass() {
const allowedSizes = ['sm', 'm', 'l', 'xl', 'xxl'];
this.sizeClass = allowedSizes.includes(this.size)
? `ball-${this.size}`
: 'ball-l';
}
static ɵfac = i0.ɵɵngDeclareFactory({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: GroupixSpinnerComponent, deps: [], target: i0.ɵɵFactoryTarget.Component });
static ɵcmp = i0.ɵɵngDeclareComponent({ minVersion: "14.0.0", version: "18.2.13", type: GroupixSpinnerComponent, selector: "groupix-spinner", inputs: { ballCount: "ballCount", size: "size" }, usesOnChanges: true, ngImport: i0, template: `
<div class="loader-container">
<div
*ngFor="let ball of balls; let i = index"
class="ball"
[ngClass]="['ball-' + (i + 1), sizeClass]"
[ngStyle]="{ 'animation-delay': -0.3 + i * 0.05 + 's' }"
></div>
</div>
`, isInline: true, styles: [".loader-container{display:flex;justify-content:center;align-items:center;height:100%;gap:8px}.ball{border-radius:50%;box-shadow:0 4px 6px #0000001a;animation:bounce 1.5s infinite ease-in-out;transition:transform .3s ease-in-out}.ball-sm{width:20px;height:20px}.ball-m{width:30px;height:30px}.ball-l{width:40px;height:40px}.ball-xl{width:50px;height:50px}.ball-xxl{width:60px;height:60px}.ball-1{background:linear-gradient(to right,#6366f1,#ec4899)}.ball-2{background:linear-gradient(to right,#facc15,#dc2626)}.ball-3{background:linear-gradient(to right,#a855f7,#2563eb)}.ball-4{background:linear-gradient(to right,#10b981,#3b82f6)}.ball-5{background:linear-gradient(to right,#f97316,#8b5cf6)}.ball-6{background:linear-gradient(to right,#06b6d4,#f43f5e)}.ball-7{background:linear-gradient(to right,#84cc16,#d946ef)}.ball-8{background:linear-gradient(to right,#14b8a6,#f59e0b)}.ball-9{background:linear-gradient(to right,#6366f1,#84cc16)}.ball:hover{transform:scale(1.25)}@keyframes bounce{0%,to{transform:translateY(0)}50%{transform:translateY(-20px)}}\n"], dependencies: [{ kind: "directive", type: i1.NgClass, selector: "[ngClass]", inputs: ["class", "ngClass"] }, { kind: "directive", type: i1.NgForOf, selector: "[ngFor][ngForOf]", inputs: ["ngForOf", "ngForTrackBy", "ngForTemplate"] }, { kind: "directive", type: i1.NgStyle, selector: "[ngStyle]", inputs: ["ngStyle"] }] });
}
i0.ɵɵngDeclareClassMetadata({ minVersion: "12.0.0", version: "18.2.13", ngImport: i0, type: GroupixSpinnerComponent, decorators: [{
type: Component,
args: [{ selector: 'groupix-spinner', template: `
<div class="loader-container">
<div
*ngFor="let ball of balls; let i = index"
class="ball"
[ngClass]="['ball-' + (i + 1), sizeClass]"
[ngStyle]="{ 'animation-delay': -0.3 + i * 0.05 + 's' }"
></div>
</div>
`, styles: [".loader-container{display:flex;justify-content:center;align-items:center;height:100%;gap:8px}.ball{border-radius:50%;box-shadow:0 4px 6px #0000001a;animation:bounce 1.5s infinite ease-in-out;transition:transform .3s ease-in-out}.ball-sm{width:20px;height:20px}.ball-m{width:30px;height:30px}.ball-l{width:40px;height:40px}.ball-xl{width:50px;height:50px}.ball-xxl{width:60px;height:60px}.ball-1{background:linear-gradient(to right,#6366f1,#ec4899)}.ball-2{background:linear-gradient(to right,#facc15,#dc2626)}.ball-3{background:linear-gradient(to right,#a855f7,#2563eb)}.ball-4{background:linear-gradient(to right,#10b981,#3b82f6)}.ball-5{background:linear-gradient(to right,#f97316,#8b5cf6)}.ball-6{background:linear-gradient(to right,#06b6d4,#f43f5e)}.ball-7{background:linear-gradient(to right,#84cc16,#d946ef)}.ball-8{background:linear-gradient(to right,#14b8a6,#f59e0b)}.ball-9{background:linear-gradient(to right,#6366f1,#84cc16)}.ball:hover{transform:scale(1.25)}@keyframes bounce{0%,to{transform:translateY(0)}50%{transform:translateY(-20px)}}\n"] }]
}], propDecorators: { ballCount: [{
type: Input
}], size: [{
type: Input
}] } });
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiZ3JvdXBpeC1zcGlubmVyLmNvbXBvbmVudC5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uL3Byb2plY3RzL2dyb3VwaXgtc3Bpbm5lci9zcmMvbGliL2dyb3VwaXgtc3Bpbm5lci5jb21wb25lbnQudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsT0FBTyxFQUFFLFNBQVMsRUFBRSxLQUFLLEVBQXFCLE1BQU0sZUFBZSxDQUFDOzs7QUErRXBFLE1BQU0sT0FBTyx1QkFBdUI7SUFDekIsU0FBUyxHQUFHLENBQUMsQ0FBQztJQUNkLElBQUksR0FBb0MsR0FBRyxDQUFDO0lBRXJELEtBQUssR0FBYSxFQUFFLENBQUM7SUFDckIsU0FBUyxHQUFHLFFBQVEsQ0FBQztJQUVyQixRQUFRO1FBQ04sSUFBSSxDQUFDLGVBQWUsRUFBRSxDQUFDO1FBQ3ZCLElBQUksQ0FBQyxlQUFlLEVBQUUsQ0FBQztJQUN6QixDQUFDO0lBRUQsV0FBVztRQUNULElBQUksQ0FBQyxlQUFlLEVBQUUsQ0FBQztRQUN2QixJQUFJLENBQUMsZUFBZSxFQUFFLENBQUM7SUFDekIsQ0FBQztJQUVPLGVBQWU7UUFDckIsTUFBTSxLQUFLLEdBQUcsSUFBSSxDQUFDLEdBQUcsQ0FBQyxJQUFJLENBQUMsR0FBRyxDQUFDLElBQUksQ0FBQyxTQUFTLEVBQUUsQ0FBQyxDQUFDLEVBQUUsQ0FBQyxDQUFDLENBQUM7UUFDdkQsSUFBSSxDQUFDLEtBQUssR0FBRyxLQUFLLENBQUMsSUFBSSxDQUFDLEVBQUUsTUFBTSxFQUFFLEtBQUssRUFBRSxFQUFFLENBQUMsQ0FBQyxFQUFFLENBQUMsRUFBRSxFQUFFLENBQUMsQ0FBQyxDQUFDLENBQUM7SUFDMUQsQ0FBQztJQUVPLGVBQWU7UUFDckIsTUFBTSxZQUFZLEdBQUcsQ0FBQyxJQUFJLEVBQUUsR0FBRyxFQUFFLEdBQUcsRUFBRSxJQUFJLEVBQUUsS0FBSyxDQUFDLENBQUM7UUFDbkQsSUFBSSxDQUFDLFNBQVMsR0FBRyxZQUFZLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUM7WUFDL0MsQ0FBQyxDQUFDLFFBQVEsSUFBSSxDQUFDLElBQUksRUFBRTtZQUNyQixDQUFDLENBQUMsUUFBUSxDQUFDO0lBQ2YsQ0FBQzt3R0EzQlUsdUJBQXVCOzRGQUF2Qix1QkFBdUIsOEhBM0V4Qjs7Ozs7Ozs7O0dBU1Q7OzRGQWtFVSx1QkFBdUI7a0JBN0VuQyxTQUFTOytCQUNFLGlCQUFpQixZQUNqQjs7Ozs7Ozs7O0dBU1Q7OEJBbUVRLFNBQVM7c0JBQWpCLEtBQUs7Z0JBQ0csSUFBSTtzQkFBWixLQUFLIiwic291cmNlc0NvbnRlbnQiOlsiaW1wb3J0IHsgQ29tcG9uZW50LCBJbnB1dCwgT25DaGFuZ2VzLCBPbkluaXQgfSBmcm9tICdAYW5ndWxhci9jb3JlJztcblxuQENvbXBvbmVudCh7XG4gIHNlbGVjdG9yOiAnZ3JvdXBpeC1zcGlubmVyJyxcbiAgdGVtcGxhdGU6IGBcbiAgICA8ZGl2IGNsYXNzPVwibG9hZGVyLWNvbnRhaW5lclwiPlxuICAgICAgPGRpdlxuICAgICAgICAqbmdGb3I9XCJsZXQgYmFsbCBvZiBiYWxsczsgbGV0IGkgPSBpbmRleFwiXG4gICAgICAgIGNsYXNzPVwiYmFsbFwiXG4gICAgICAgIFtuZ0NsYXNzXT1cIlsnYmFsbC0nICsgKGkgKyAxKSwgc2l6ZUNsYXNzXVwiXG4gICAgICAgIFtuZ1N0eWxlXT1cInsgJ2FuaW1hdGlvbi1kZWxheSc6IC0wLjMgKyBpICogMC4wNSArICdzJyB9XCJcbiAgICAgID48L2Rpdj5cbiAgICA8L2Rpdj5cbiAgYCxcbiAgc3R5bGVzOiBgXG4gICAgLmxvYWRlci1jb250YWluZXIge1xuICAgICAgZGlzcGxheTogZmxleDtcbiAgICAgIGp1c3RpZnktY29udGVudDogY2VudGVyO1xuICAgICAgYWxpZ24taXRlbXM6IGNlbnRlcjtcbiAgICAgIGhlaWdodDogMTAwJTtcbiAgICAgIGdhcDogOHB4O1xuICAgIH1cblxuICAgIC5iYWxsIHtcbiAgICAgIGJvcmRlci1yYWRpdXM6IDUwJTtcbiAgICAgIGJveC1zaGFkb3c6IDBweCA0cHggNnB4IHJnYmEoMCwgMCwgMCwgMC4xKTtcbiAgICAgIGFuaW1hdGlvbjogYm91bmNlIDEuNXMgaW5maW5pdGUgZWFzZS1pbi1vdXQ7XG4gICAgICB0cmFuc2l0aW9uOiB0cmFuc2Zvcm0gMC4zcyBlYXNlLWluLW91dDtcbiAgICB9XG5cbiAgICAuYmFsbC1zbSB7XG4gICAgICB3aWR0aDogMjBweDtcbiAgICAgIGhlaWdodDogMjBweDtcbiAgICB9XG5cbiAgICAuYmFsbC1tIHtcbiAgICAgIHdpZHRoOiAzMHB4O1xuICAgICAgaGVpZ2h0OiAzMHB4O1xuICAgIH1cblxuICAgIC5iYWxsLWwge1xuICAgICAgd2lkdGg6IDQwcHg7XG4gICAgICBoZWlnaHQ6IDQwcHg7XG4gICAgfVxuXG4gICAgLmJhbGwteGwge1xuICAgICAgd2lkdGg6IDUwcHg7XG4gICAgICBoZWlnaHQ6IDUwcHg7XG4gICAgfVxuXG4gICAgLmJhbGwteHhsIHtcbiAgICAgIHdpZHRoOiA2MHB4O1xuICAgICAgaGVpZ2h0OiA2MHB4O1xuICAgIH1cblxuICAgIC5iYWxsLTEgeyBiYWNrZ3JvdW5kOiBsaW5lYXItZ3JhZGllbnQodG8gcmlnaHQsICM2MzY2ZjEsICNlYzQ4OTkpOyB9XG4gICAgLmJhbGwtMiB7IGJhY2tncm91bmQ6IGxpbmVhci1ncmFkaWVudCh0byByaWdodCwgI2ZhY2MxNSwgI2RjMjYyNik7IH1cbiAgICAuYmFsbC0zIHsgYmFja2dyb3VuZDogbGluZWFyLWdyYWRpZW50KHRvIHJpZ2h0LCAjYTg1NWY3LCAjMjU2M2ViKTsgfVxuICAgIC5iYWxsLTQgeyBiYWNrZ3JvdW5kOiBsaW5lYXItZ3JhZGllbnQodG8gcmlnaHQsICMxMGI5ODEsICMzYjgyZjYpOyB9XG4gICAgLmJhbGwtNSB7IGJhY2tncm91bmQ6IGxpbmVhci1ncmFkaWVudCh0byByaWdodCwgI2Y5NzMxNiwgIzhiNWNmNik7IH1cbiAgICAuYmFsbC02IHsgYmFja2dyb3VuZDogbGluZWFyLWdyYWRpZW50KHRvIHJpZ2h0LCAjMDZiNmQ0LCAjZjQzZjVlKTsgfVxuICAgIC5iYWxsLTcgeyBiYWNrZ3JvdW5kOiBsaW5lYXItZ3JhZGllbnQodG8gcmlnaHQsICM4NGNjMTYsICNkOTQ2ZWYpOyB9XG4gICAgLmJhbGwtOCB7IGJhY2tncm91bmQ6IGxpbmVhci1ncmFkaWVudCh0byByaWdodCwgIzE0YjhhNiwgI2Y1OWUwYik7IH1cbiAgICAuYmFsbC05IHsgYmFja2dyb3VuZDogbGluZWFyLWdyYWRpZW50KHRvIHJpZ2h0LCAjNjM2NmYxLCAjODRjYzE2KTsgfVxuXG4gICAgLmJhbGw6aG92ZXIge1xuICAgICAgdHJhbnNmb3JtOiBzY2FsZSgxLjI1KTtcbiAgICB9XG5cbiAgICBAa2V5ZnJhbWVzIGJvdW5jZSB7XG4gICAgICAwJSwgMTAwJSB7XG4gICAgICAgIHRyYW5zZm9ybTogdHJhbnNsYXRlWSgwKTtcbiAgICAgIH1cbiAgICAgIDUwJSB7XG4gICAgICAgIHRyYW5zZm9ybTogdHJhbnNsYXRlWSgtMjBweCk7XG4gICAgICB9XG4gICAgfVxuICBgLFxufSlcbmV4cG9ydCBjbGFzcyBHcm91cGl4U3Bpbm5lckNvbXBvbmVudCBpbXBsZW1lbnRzIE9uQ2hhbmdlcywgT25Jbml0IHtcbiAgQElucHV0KCkgYmFsbENvdW50ID0gMztcbiAgQElucHV0KCkgc2l6ZTogJ3NtJyB8ICdtJyB8ICdsJyB8ICd4bCcgfCAneHhsJyA9ICdsJztcblxuICBiYWxsczogbnVtYmVyW10gPSBbXTtcbiAgc2l6ZUNsYXNzID0gJ2JhbGwtbCc7XG5cbiAgbmdPbkluaXQoKTogdm9pZCB7XG4gICAgdGhpcy51cGRhdGVCYWxsQ291bnQoKTtcbiAgICB0aGlzLnVwZGF0ZVNpemVDbGFzcygpO1xuICB9XG5cbiAgbmdPbkNoYW5nZXMoKTogdm9pZCB7XG4gICAgdGhpcy51cGRhdGVCYWxsQ291bnQoKTtcbiAgICB0aGlzLnVwZGF0ZVNpemVDbGFzcygpO1xuICB9XG5cbiAgcHJpdmF0ZSB1cGRhdGVCYWxsQ291bnQoKTogdm9pZCB7XG4gICAgY29uc3QgY291bnQgPSBNYXRoLm1pbihNYXRoLm1heCh0aGlzLmJhbGxDb3VudCwgMyksIDkpO1xuICAgIHRoaXMuYmFsbHMgPSBBcnJheS5mcm9tKHsgbGVuZ3RoOiBjb3VudCB9LCAoXywgaSkgPT4gaSk7XG4gIH1cblxuICBwcml2YXRlIHVwZGF0ZVNpemVDbGFzcygpOiB2b2lkIHtcbiAgICBjb25zdCBhbGxvd2VkU2l6ZXMgPSBbJ3NtJywgJ20nLCAnbCcsICd4bCcsICd4eGwnXTtcbiAgICB0aGlzLnNpemVDbGFzcyA9IGFsbG93ZWRTaXplcy5pbmNsdWRlcyh0aGlzLnNpemUpXG4gICAgICA/IGBiYWxsLSR7dGhpcy5zaXplfWBcbiAgICAgIDogJ2JhbGwtbCc7XG4gIH1cbn1cbiJdfQ==