Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Story Group Event Emitter #38

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 11 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -58,8 +58,16 @@ export class AppComponent {
| `triggerOnEnd` | `EventEmitter<void>` | No | Output event that is triggered when the user reaches the end of all stories. |
| `triggerOnExit` | `EventEmitter<void>` | No | Output event that is triggered when the user manually exits the story view. |
| `triggerOnSwipeUp` | `EventEmitter<void>` | No | Output event that is triggered when the user performs a swipe-up gesture, typically for additional actions. |
| `onStoryGroupChange` | `EventEmitter<number>` | No | Output event that is triggered when the user changes the storyGroup.


```ts
interface NgxStoriesOptions {
width: number,
height: number,
}
```

## Features
* Dynamic Story Carousel: Display a collection of stories for each storyGroup.
* Easy Integration: Simple and straightforward to integrate into your Angular project.
Expand All @@ -68,5 +76,8 @@ export class AppComponent {
* Hold to Pause: Pause the story progress when the user holds their finger on the screen.
* Events: Trigger events when the user reaches the end of the stories or when they exit the carousel.

## Contributing
[Contributing Guide](https://github.com/Gauravdarkslayer/ngx-stories/blob/main/CONTRIBUTING.md)

## License
This library is licensed under the MIT License. Feel free to use and modify the code as per your needs.
16 changes: 15 additions & 1 deletion projects/ngx-stories/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,9 @@

An Angular library for displaying user stories in a carousel format.

[![npm downloads](https://img.shields.io/npm/dt/ngx-stories)](https://www.npmjs.com/package/ngx-stories)
[![npm version](https://img.shields.io/npm/v/ngx-stories)](https://www.npmjs.com/package/ngx-stories)


## For Version 17+

Expand Down Expand Up @@ -55,8 +58,16 @@ export class AppComponent {
| `triggerOnEnd` | `EventEmitter<void>` | No | Output event that is triggered when the user reaches the end of all stories. |
| `triggerOnExit` | `EventEmitter<void>` | No | Output event that is triggered when the user manually exits the story view. |
| `triggerOnSwipeUp` | `EventEmitter<void>` | No | Output event that is triggered when the user performs a swipe-up gesture, typically for additional actions. |
| `onStoryGroupChange` | `EventEmitter<number>` | No | Output event that is triggered when the user changes the storyGroup.


```ts
interface NgxStoriesOptions {
width: number,
height: number,
}
```

## Features
* Dynamic Story Carousel: Display a collection of stories for each storyGroup.
* Easy Integration: Simple and straightforward to integrate into your Angular project.
Expand All @@ -65,5 +76,8 @@ export class AppComponent {
* Hold to Pause: Pause the story progress when the user holds their finger on the screen.
* Events: Trigger events when the user reaches the end of the stories or when they exit the carousel.

## Contributing
[Contributing Guide](https://github.com/Gauravdarkslayer/ngx-stories/blob/main/CONTRIBUTING.md)

## License
This library is licensed under the MIT License. Feel free to use and modify the code as per your needs.
This library is licensed under the MIT License. Feel free to use and modify the code as per your needs.
2 changes: 1 addition & 1 deletion projects/ngx-stories/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "ngx-stories",
"version": "0.0.7-beta.8",
"version": "0.0.7-beta.9",
"peerDependencies": {
"@angular/common": "^18.2.0",
"@angular/core": "^18.2.0",
Expand Down
22 changes: 15 additions & 7 deletions projects/ngx-stories/src/lib/ngx-stories.component.ts
Original file line number Diff line number Diff line change
@@ -1,11 +1,12 @@
import { AfterViewInit, Component, ElementRef, EventEmitter, Input, Output, QueryList, ViewChildren } from '@angular/core';
import { AfterViewInit, Component, ElementRef, Input, Output, QueryList, ViewChildren } from '@angular/core';
import { RouterOutlet } from '@angular/router';
import { HammerModule } from '@angular/platform-browser';
import { StoryGroup } from '../lib/interfaces/interfaces';
import "hammerjs";
import { CommonModule } from '@angular/common';
import { NgxStoriesService } from './ngx-stories.service';
import { NgxStoriesOptions } from '../lib/interfaces/interfaces';
import { onStoryGroupChange, triggerOnEnd, triggerOnExit, triggerOnSwipeUp } from './utils/story-event-emitters';
import "hammerjs";

@Component({
selector: 'ngx-stories',
Expand All @@ -26,9 +27,10 @@ export class NgxStoriesComponent implements AfterViewInit {
height: 768,
};
// Output events to handle end of stories, exit, and swipe-up gesture
@Output() triggerOnEnd = new EventEmitter<void>();
@Output() triggerOnExit = new EventEmitter<void>();
@Output() triggerOnSwipeUp = new EventEmitter<void>();
@Output() triggerOnEnd = triggerOnEnd;
@Output() triggerOnExit = triggerOnExit;
@Output() triggerOnSwipeUp = triggerOnSwipeUp;
@Output() onStoryGroupChange = onStoryGroupChange;

currentStoryIndex: number = 0;
currentStoryGroupIndex: number = 0;
Expand Down Expand Up @@ -125,8 +127,8 @@ export class NgxStoriesComponent implements AfterViewInit {

const { storyGroupIndex, storyIndex } =
direction === 'next'
? this.storyService.nextStory(this.storyGroups, this.currentStoryGroupIndex, this.currentStoryIndex)
: this.storyService.prevStory(this.storyGroups, this.currentStoryGroupIndex, this.currentStoryIndex);
? this.storyService.nextStory(this.storyGroups, this.currentStoryGroupIndex, this.currentStoryIndex, this.storyGroupChange.bind(this))
: this.storyService.prevStory(this.storyGroups, this.currentStoryGroupIndex, this.currentStoryIndex, this.storyGroupChange.bind(this));

this.currentStoryGroupIndex = storyGroupIndex;
this.currentStoryIndex = storyIndex;
Expand All @@ -144,6 +146,7 @@ export class NgxStoriesComponent implements AfterViewInit {
this.currentStoryIndex = 0;
clearInterval(this.intervalId);
this.progressWidth = 0;
this.storyGroupChange();
setTimeout(() => {
this.startStoryProgress();
this.isTransitioning = false;
Expand All @@ -159,6 +162,7 @@ export class NgxStoriesComponent implements AfterViewInit {
this.currentStoryGroupIndex--;
}
this.progressWidth = 0;
this.storyGroupChange();
setTimeout(() => {
this.startStoryProgress();
this.isTransitioning = false;
Expand Down Expand Up @@ -234,4 +238,8 @@ export class NgxStoriesComponent implements AfterViewInit {
private onSwipeUpTriggered() {
this.triggerOnSwipeUp.emit();
}

private storyGroupChange(storyGroupIndex: number = this.currentStoryGroupIndex) {
this.onStoryGroupChange.emit(storyGroupIndex);
}
}
14 changes: 8 additions & 6 deletions projects/ngx-stories/src/lib/ngx-stories.service.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,10 +5,12 @@ import { StoryGroup } from './interfaces/interfaces';

describe('NgxStoriesService', () => {
let service: NgxStoriesService;
let onStoryGroupChangeMock: jasmine.Spy;

beforeEach(() => {
TestBed.configureTestingModule({});
service = TestBed.inject(NgxStoriesService);
onStoryGroupChangeMock = jasmine.createSpy('onStoryGroupChange');
});

it('should be created', () => {
Expand Down Expand Up @@ -67,13 +69,13 @@ describe('NgxStoriesService', () => {
];

it('should move to the next story within the same storyGroup', () => {
const result = service.nextStory(storyGroups, 0, 0); // Start at storyGroup 0, story 0
const result = service.nextStory(storyGroups, 0, 0, onStoryGroupChangeMock); // Start at storyGroup 0, story 0
expect(result.storyGroupIndex).toBe(0);
expect(result.storyIndex).toBe(1);
});

it('should move to the next storyGroup if current story is the last one', () => {
const result = service.nextStory(storyGroups, 0, 2); // Start at storyGroup 0, story 2 (last story)
const result = service.nextStory(storyGroups, 0, 2, onStoryGroupChangeMock); // Start at storyGroup 0, story 2 (last story)
expect(result.storyGroupIndex).toBe(1); // Moved to next storyGroup
expect(result.storyIndex).toBe(0); // First story of the next storyGroup
});
Expand Down Expand Up @@ -103,22 +105,22 @@ describe('NgxStoriesService', () => {
];

it('should move to the previous story within the same storyGroup', () => {
const result = service.prevStory(storyGroups, 0, 2); // Start at storyGroup 0, story 2
const result = service.prevStory(storyGroups, 0, 2, onStoryGroupChangeMock); // Start at storyGroup 0, story 2
expect(result.storyGroupIndex).toBe(0);
expect(result.storyIndex).toBe(1);
});

it('should move to the previous storyGroup if current story is the first one', () => {
const result = service.prevStory(storyGroups, 1, 0); // Start at storyGroup 1, story 0
const result = service.prevStory(storyGroups, 1, 0, onStoryGroupChangeMock); // Start at storyGroup 1, story 0
expect(result.storyGroupIndex).toBe(0); // Moved to previous storyGroup
expect(result.storyIndex).toBe(2); // Last story of the previous storyGroup
});

it('should do nothing if on the first story of the first storyGroup', () => {
const result = service.prevStory(storyGroups, 0, 0); // First story of the first storyGroup
const result = service.prevStory(storyGroups, 0, 0, onStoryGroupChangeMock); // First story of the first storyGroup
expect(result.storyGroupIndex).toBe(0);
expect(result.storyIndex).toBe(0); // Remains at the first story
});
});

});
12 changes: 10 additions & 2 deletions projects/ngx-stories/src/lib/ngx-stories.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,27 +17,35 @@ export class NgxStoriesService {
clearInterval(intervalId);
}

nextStory(storyGroups: StoryGroup[], currentStoryGroupIndex: number, currentStoryIndex: number): { storyGroupIndex: number, storyIndex: number } {
nextStory(storyGroups: StoryGroup[],
currentStoryGroupIndex: number,
currentStoryIndex: number,
onStoryGroupChange: (storyGroupIndex: number) => void): { storyGroupIndex: number, storyIndex: number } {
let stories = storyGroups[currentStoryGroupIndex]?.stories;
if (currentStoryIndex === stories.length - 1) {
// Move to the next storyGroup if the current story index is the last
currentStoryGroupIndex = (currentStoryGroupIndex + 1) % storyGroups.length;
currentStoryIndex = 0;
onStoryGroupChange(currentStoryGroupIndex);
} else {
// Otherwise, just move to the next story within the same storyGroup
currentStoryIndex++;
}
return { storyGroupIndex: currentStoryGroupIndex, storyIndex: currentStoryIndex };
}

prevStory(storyGroups: StoryGroup[], currentStoryGroupIndex: number, currentStoryIndex: number): { storyGroupIndex: number, storyIndex: number } {
prevStory(storyGroups: StoryGroup[],
currentStoryGroupIndex: number,
currentStoryIndex: number,
onStoryGroupChange: (storyGroupIndex: number) => void): { storyGroupIndex: number, storyIndex: number } {
let stories = storyGroups[currentStoryGroupIndex]?.stories;
if (currentStoryIndex === 0) {
// Move to the previous storyGroup if the current story index is 0
if (currentStoryGroupIndex > 0) {
currentStoryGroupIndex--;
stories = storyGroups[currentStoryGroupIndex]?.stories;
currentStoryIndex = stories.length - 1;
onStoryGroupChange(currentStoryGroupIndex);
}
} else {
// Otherwise, just move to the previous story within the same storyGroup
Expand Down
6 changes: 6 additions & 0 deletions projects/ngx-stories/src/lib/utils/story-event-emitters.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
import { EventEmitter } from '@angular/core';

export const triggerOnEnd: EventEmitter<void> = new EventEmitter<void>();
export const triggerOnExit: EventEmitter<void> = new EventEmitter<void>();
export const triggerOnSwipeUp: EventEmitter<void> = new EventEmitter<void>();
export const onStoryGroupChange: EventEmitter<number> = new EventEmitter<number>();
1 change: 1 addition & 0 deletions src/app/app.component.html
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,5 @@ <h1>Ngx-Stories Demo</h1>
[storyGroups]="storyGroups"
(triggerOnEnd)="triggerOnEnd()"
(triggerOnExit)="triggerOnExit()"
(onStoryGroupChange)="triggerOnStoryGroupChange($event)"
></ngx-stories>
4 changes: 4 additions & 0 deletions src/app/app.component.ts
Original file line number Diff line number Diff line change
Expand Up @@ -38,4 +38,8 @@ export class AppComponent {
triggerOnExit() {
alert('Exit');
}

triggerOnStoryGroupChange(storyGroup: number) {
console.log(storyGroup);
}
}
Loading