diff --git a/src/app/app.component.html b/src/app/app.component.html index 2934ad1..829768c 100644 --- a/src/app/app.component.html +++ b/src/app/app.component.html @@ -1 +1,2 @@ - + + \ No newline at end of file diff --git a/src/app/app.component.ts b/src/app/app.component.ts index f33c411..54eb120 100644 --- a/src/app/app.component.ts +++ b/src/app/app.component.ts @@ -1,10 +1,12 @@ import { Component } from '@angular/core'; import { HomeComponent } from './pages/home/home.component'; +import { NavbarComponent } from "./components/navbar/navbar.component"; +import { RouterModule } from '@angular/router'; @Component({ selector: 'app-root', standalone: true, - imports: [HomeComponent], + imports: [HomeComponent, NavbarComponent, RouterModule], templateUrl: './app.component.html', styleUrl: './app.component.css' }) diff --git a/src/app/app.routes.ts b/src/app/app.routes.ts index dc39edb..889b3ef 100644 --- a/src/app/app.routes.ts +++ b/src/app/app.routes.ts @@ -1,3 +1,24 @@ import { Routes } from '@angular/router'; -export const routes: Routes = []; +export const routes: Routes = [ + { + path: '', + loadComponent: () => + import('./pages/home/home.component').then(m => m.HomeComponent) + },{ + path: 'trips', + loadComponent: () => + import('./pages/trips-list/trips-list.component').then(m => m.TripsListComponent) + },{ + path: 'trips/:id', + loadComponent: () => + import('./pages/trip/trip.component').then(m => m.TripComponent) + }, + { + path: '**', + redirectTo: '', + },{ + path: '**', + redirectTo: '', + } +]; diff --git a/src/app/components/navbar/navbar.component.html b/src/app/components/navbar/navbar.component.html index 86bcc47..f02db72 100644 --- a/src/app/components/navbar/navbar.component.html +++ b/src/app/components/navbar/navbar.component.html @@ -6,10 +6,10 @@ diff --git a/src/app/components/navbar/navbar.component.ts b/src/app/components/navbar/navbar.component.ts index aef9405..fc70984 100644 --- a/src/app/components/navbar/navbar.component.ts +++ b/src/app/components/navbar/navbar.component.ts @@ -1,9 +1,10 @@ import { Component } from '@angular/core'; +import { RouterModule } from '@angular/router'; @Component({ selector: 'app-navbar', standalone: true, - imports: [], + imports: [RouterModule], templateUrl: './navbar.component.html', styleUrl: './navbar.component.css' }) diff --git a/src/app/components/search-filter/search-filter.component.html b/src/app/components/search-filter/search-filter.component.html index 5df8e03..1603e14 100644 --- a/src/app/components/search-filter/search-filter.component.html +++ b/src/app/components/search-filter/search-filter.component.html @@ -3,7 +3,9 @@ type="search" class="search-input" placeholder="Search" - (input)="onSearch($event)" + #search + [value]="searchString" + (input)="onSearch(search.value)" />
@for (level of difficultyLevels; track $index) { diff --git a/src/app/components/search-filter/search-filter.component.ts b/src/app/components/search-filter/search-filter.component.ts index cf02263..cd316a5 100644 --- a/src/app/components/search-filter/search-filter.component.ts +++ b/src/app/components/search-filter/search-filter.component.ts @@ -1,5 +1,6 @@ import { Component, EventEmitter, Output } from '@angular/core'; import { DifficultyLevel } from '../../../data/trips'; +import { ActivatedRoute, Router } from '@angular/router'; @Component({ selector: 'app-search-filter', @@ -14,10 +15,28 @@ export class SearchFilterComponent { difficultyLevels: DifficultyLevel[] = ['All','Easy', 'Moderate', 'Hard']; activeFilter: DifficultyLevel = 'All'; + searchString: string = ''; - onSearch(event: Event) { - const inputElement = event.target as HTMLInputElement; - this.searchChange.emit(inputElement.value); + constructor(private route: ActivatedRoute, private router: Router) { + this.route.queryParams.subscribe((params) => { + const difficulty = params['difficulty'] as DifficultyLevel; + const search = params['search'] as string; + + if (difficulty && ['Easy', 'Medium', 'Hard'].includes(difficulty)) { + this.filterByDifficulty(difficulty); + } + + if(search != '' && search != undefined) + { + this.searchString = search + this.onSearch(search) + } + }); + } + + onSearch(srch: string){//event: Event) { + // const inputElement = event.target as HTMLInputElement; + this.searchChange.emit(srch);//inputElement.value); } filterByDifficulty(level: DifficultyLevel) { diff --git a/src/app/components/trips-grid/trips-grid.component.html b/src/app/components/trips-grid/trips-grid.component.html index 2829032..d823108 100644 --- a/src/app/components/trips-grid/trips-grid.component.html +++ b/src/app/components/trips-grid/trips-grid.component.html @@ -1,5 +1,5 @@
@for (trip of trips; track trip.id) { - + }
diff --git a/src/app/components/trips-grid/trips-grid.component.ts b/src/app/components/trips-grid/trips-grid.component.ts index c0d5289..22b2bc1 100644 --- a/src/app/components/trips-grid/trips-grid.component.ts +++ b/src/app/components/trips-grid/trips-grid.component.ts @@ -1,11 +1,12 @@ import { Component, Input } from '@angular/core'; import { Trip } from '../../../data/trips'; import { TripCardComponent } from '../trip-card/trip-card.component'; +import { RouterModule } from '@angular/router'; @Component({ selector: 'app-trips-grid', standalone: true, - imports: [TripCardComponent], + imports: [TripCardComponent, RouterModule], templateUrl: './trips-grid.component.html', styleUrl: './trips-grid.component.css' }) diff --git a/src/app/pages/home/home.component.html b/src/app/pages/home/home.component.html index 08171ab..9f2c545 100644 --- a/src/app/pages/home/home.component.html +++ b/src/app/pages/home/home.component.html @@ -1,25 +1,4 @@ - - - -
-
-

Explore Trips

-
- - - -
-
- -@if (selectedTrip) { - -} diff --git a/src/app/pages/home/home.component.ts b/src/app/pages/home/home.component.ts index 00f224f..59aebd3 100644 --- a/src/app/pages/home/home.component.ts +++ b/src/app/pages/home/home.component.ts @@ -22,34 +22,5 @@ import { NavbarComponent } from '../../components/navbar/navbar.component'; styleUrl: './home.component.css', }) export class HomeComponent { - trips: Trip[] = trips; - filteredTrips: Trip[] = [...trips]; - selectedTrip: Trip = trips[0]; - searchQuery: string = ''; - activeDifficultyFilter: DifficultyLevel = 'All'; - handleSearch(searchTerm: string) { - this.searchQuery = searchTerm.toLowerCase(); - this.applyFilters(); - } - - handleFilter(difficulty: DifficultyLevel) { - this.activeDifficultyFilter = difficulty; - this.applyFilters(); - } - - private applyFilters() { - this.filteredTrips = this.trips.filter((trip) => { - const matchesSearch = - !this.searchQuery || - trip.name.toLowerCase().includes(this.searchQuery.toLowerCase()) || - trip.city.toLowerCase().includes(this.searchQuery.toLowerCase()) - - const matchesDifficulty = - this.activeDifficultyFilter === 'All' || - trip.difficulty === this.activeDifficultyFilter; - - return matchesSearch && matchesDifficulty; - }); - } } diff --git a/src/app/pages/trip/trip.component.css b/src/app/pages/trip/trip.component.css new file mode 100644 index 0000000..e69de29 diff --git a/src/app/pages/trip/trip.component.html b/src/app/pages/trip/trip.component.html new file mode 100644 index 0000000..b2a96c1 --- /dev/null +++ b/src/app/pages/trip/trip.component.html @@ -0,0 +1,3 @@ +@if (selectedTrip) { + + } \ No newline at end of file diff --git a/src/app/pages/trip/trip.component.spec.ts b/src/app/pages/trip/trip.component.spec.ts new file mode 100644 index 0000000..4c19a5b --- /dev/null +++ b/src/app/pages/trip/trip.component.spec.ts @@ -0,0 +1,23 @@ +import { ComponentFixture, TestBed } from '@angular/core/testing'; + +import { TripComponent } from './trip.component'; + +describe('TripComponent', () => { + let component: TripComponent; + let fixture: ComponentFixture; + + beforeEach(async () => { + await TestBed.configureTestingModule({ + imports: [TripComponent] + }) + .compileComponents(); + + fixture = TestBed.createComponent(TripComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/src/app/pages/trip/trip.component.ts b/src/app/pages/trip/trip.component.ts new file mode 100644 index 0000000..8eb1f82 --- /dev/null +++ b/src/app/pages/trip/trip.component.ts @@ -0,0 +1,23 @@ +import { Component } from '@angular/core'; +import { TripDetailsComponent } from "../../components/trip-details/trip-details.component"; +import { Trip, trips } from '../../../data/trips'; +import { ActivatedRoute, Router } from '@angular/router'; + +@Component({ + selector: 'app-trip', + standalone: true, + imports: [TripDetailsComponent], + templateUrl: './trip.component.html', + styleUrl: './trip.component.css' +}) +export class TripComponent { + selectedTrip: Trip | undefined; + + constructor(private route: ActivatedRoute, private router: Router) { + const id = +this.route.snapshot.paramMap.get('id')!; + this.selectedTrip = trips.find((trip) => trip.id === id); + if (!this.selectedTrip) { + this.router.navigate(['/trips']); + } + } +} diff --git a/src/app/pages/trips-list/trips-list.component.css b/src/app/pages/trips-list/trips-list.component.css new file mode 100644 index 0000000..e69de29 diff --git a/src/app/pages/trips-list/trips-list.component.html b/src/app/pages/trips-list/trips-list.component.html new file mode 100644 index 0000000..f53ceff --- /dev/null +++ b/src/app/pages/trips-list/trips-list.component.html @@ -0,0 +1,19 @@ +
+
+

Explore Trips

+
+ + + @if(filteredTrips.length > 0){ + + } + @else { +

No trips found!

+ } +
+
\ No newline at end of file diff --git a/src/app/pages/trips-list/trips-list.component.spec.ts b/src/app/pages/trips-list/trips-list.component.spec.ts new file mode 100644 index 0000000..354f397 --- /dev/null +++ b/src/app/pages/trips-list/trips-list.component.spec.ts @@ -0,0 +1,23 @@ +import { ComponentFixture, TestBed } from '@angular/core/testing'; + +import { TripsListComponent } from './trips-list.component'; + +describe('TripsListComponent', () => { + let component: TripsListComponent; + let fixture: ComponentFixture; + + beforeEach(async () => { + await TestBed.configureTestingModule({ + imports: [TripsListComponent] + }) + .compileComponents(); + + fixture = TestBed.createComponent(TripsListComponent); + component = fixture.componentInstance; + fixture.detectChanges(); + }); + + it('should create', () => { + expect(component).toBeTruthy(); + }); +}); diff --git a/src/app/pages/trips-list/trips-list.component.ts b/src/app/pages/trips-list/trips-list.component.ts new file mode 100644 index 0000000..7c136b6 --- /dev/null +++ b/src/app/pages/trips-list/trips-list.component.ts @@ -0,0 +1,75 @@ +import { Component } from '@angular/core'; +import { Trip, trips, DifficultyLevel } from '../../../data/trips'; +import { SearchFilterComponent } from "../../components/search-filter/search-filter.component"; +import { DividerComponent } from "../../components/divider/divider.component"; +import { TripsGridComponent } from "../../components/trips-grid/trips-grid.component"; +import { ActivatedRoute, Router } from '@angular/router'; + +@Component({ + selector: 'app-trips-list', + standalone: true, + imports: [SearchFilterComponent, DividerComponent, TripsGridComponent], + templateUrl: './trips-list.component.html', + styleUrl: './trips-list.component.css' +}) +export class TripsListComponent { + trips: Trip[] = trips; + filteredTrips: Trip[] = [...trips]; + searchQuery: string = ''; + activeDifficultyFilter: DifficultyLevel = 'All'; + + constructor(private route: ActivatedRoute, private router: Router) { + this.route.queryParams.subscribe((params) => { + const difficulty = params['difficulty'] as DifficultyLevel; + const search = params['search'] as string; + + if (difficulty && ['Easy', 'Medium', 'Hard'].includes(difficulty)) { + this.activeDifficultyFilter = difficulty; + this.applyFilters(); + } + + if(search != '') + { + this.searchQuery = search; + this.applyFilters(); + } + }); + } + + handleSearch(searchTerm: string) { + this.searchQuery = searchTerm.toLowerCase(); + + this.router.navigate([], { + queryParams: { search: this.searchQuery !== '' ? this.searchQuery : null }, + queryParamsHandling: 'merge', + }); + + this.applyFilters(); + } + + handleFilter(difficulty: DifficultyLevel) { + this.activeDifficultyFilter = difficulty; + + this.router.navigate([], { + queryParams: { difficulty: difficulty !== 'All' ? difficulty : null }, + queryParamsHandling: 'merge', + }); + + this.applyFilters(); + } + + private applyFilters() { + this.filteredTrips = this.trips.filter((trip) => { + const matchesSearch = + !this.searchQuery || + trip.name.toLowerCase().includes(this.searchQuery.toLowerCase()) || + trip.city.toLowerCase().includes(this.searchQuery.toLowerCase()) + + const matchesDifficulty = + this.activeDifficultyFilter === 'All' || + trip.difficulty === this.activeDifficultyFilter; + + return matchesSearch && matchesDifficulty; + }); + } +}