Added basic cart system
This commit is contained in:
		| @@ -25,10 +25,11 @@ | |||||||
|                 </ul> |                 </ul> | ||||||
|                 <div class="ml-auto"> |                 <div class="ml-auto"> | ||||||
|                     <button *ngIf="!user" mat-stroked-button color="primary" (click)="login()">Login</button> |                     <button *ngIf="!user" mat-stroked-button color="primary" (click)="login()">Login</button> | ||||||
|                     <div *ngIf="user"> |                     <div *ngIf="user" class="d-inline"> | ||||||
|                         <span class="text-muted mr-3">{{user.email}}</span> |                         <span class="text-muted mr-3">{{user.email}}</span> | ||||||
|                         <button mat-stroked-button color="accent" (click)="afAuth.auth.signOut()">Logout</button> |                         <button mat-stroked-button color="accent" (click)="afAuth.auth.signOut()">Logout</button> | ||||||
|                     </div> |                     </div> | ||||||
|  |                     <mat-icon *ngIf="cart.length" class="ml-3" style="transform: translateY(6px)" [matBadge]="cartItemCount()" matBadgeColor="warn">shopping_cart</mat-icon> | ||||||
|                 </div> |                 </div> | ||||||
|             </div> |             </div> | ||||||
|         </div> |         </div> | ||||||
| @@ -74,7 +75,8 @@ | |||||||
|                     <h5>CONTACT</h5> |                     <h5>CONTACT</h5> | ||||||
|                     <p> |                     <p> | ||||||
|                         <i class="fas fa-phone mr-2"></i> 416-744-2723 |                         <i class="fas fa-phone mr-2"></i> 416-744-2723 | ||||||
|                         <br /><i class="fas fa-fax mr-2"></i> 416-744-4078 |                         <br /> | ||||||
|  |                         <i class="fas fa-fax mr-2"></i> 416-744-4078 | ||||||
|                         <br />Toll Free: 1-888-422-7737 |                         <br />Toll Free: 1-888-422-7737 | ||||||
|                     </p> |                     </p> | ||||||
|                 </div> |                 </div> | ||||||
| @@ -84,7 +86,8 @@ | |||||||
|     <div class="container-fluid footer-sub"> |     <div class="container-fluid footer-sub"> | ||||||
|         <div class="container text-center"> |         <div class="container text-center"> | ||||||
|             <p class="mb-0 p-2">© 2018 FH & SONS |             <p class="mb-0 p-2">© 2018 FH & SONS | ||||||
|                 <br />Designed and developed by: <a href="http://zakscode.com">Zak Timson</a> |                 <br />Designed and developed by: | ||||||
|  |                 <a href="http://zakscode.com">Zak Timson</a> | ||||||
|             </p> |             </p> | ||||||
|         </div> |         </div> | ||||||
|     </div> |     </div> | ||||||
|   | |||||||
| @@ -6,12 +6,16 @@ import {filter} from 'rxjs/operators'; | |||||||
| import {MatDialog} from '@angular/material'; | import {MatDialog} from '@angular/material'; | ||||||
| import {LoginComponent} from './login/login.component'; | import {LoginComponent} from './login/login.component'; | ||||||
| import {AngularFireAuth} from 'angularfire2/auth'; | import {AngularFireAuth} from 'angularfire2/auth'; | ||||||
|  | import {LocalStorage} from 'webstorage-decorators'; | ||||||
|  |  | ||||||
| @Component({ | @Component({ | ||||||
|   selector: 'app-root', |   selector: 'app-root', | ||||||
|   templateUrl: 'app.component.html' |   templateUrl: 'app.component.html' | ||||||
| }) | }) | ||||||
| export class AppComponent implements OnInit { | export class AppComponent implements OnInit { | ||||||
|  |   @LocalStorage({defaultValue: []}) | ||||||
|  |   cart: {id: string; item: string; price: number; quantity: number}[]; | ||||||
|  |  | ||||||
|   categories; |   categories; | ||||||
|   user; |   user; | ||||||
|  |  | ||||||
| @@ -25,6 +29,18 @@ export class AppComponent implements OnInit { | |||||||
|     this.categories = this.db.collection('categories').valueChanges(); |     this.categories = this.db.collection('categories').valueChanges(); | ||||||
|   } |   } | ||||||
|  |  | ||||||
|  |   addToCart(id: string, item: string, price: number, quantity: number) { | ||||||
|  |     this.cart = [{id: id, item: item, price: Number(price), quantity: Number(quantity)}].concat(this.cart); | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   cartItemCount() { | ||||||
|  |     return this.cart.map(row => row.quantity).reduce((acc, row) => acc + row, 0); | ||||||
|  |   } | ||||||
|  |  | ||||||
|  |   login() { | ||||||
|  |     this.dialog.open(LoginComponent); | ||||||
|  |   } | ||||||
|  |  | ||||||
|   ngOnInit() { |   ngOnInit() { | ||||||
|     // Record routing for analytics |     // Record routing for analytics | ||||||
|     this.router.events.pipe(filter(event => event instanceof NavigationEnd)).subscribe((event: NavigationEnd) => { |     this.router.events.pipe(filter(event => event instanceof NavigationEnd)).subscribe((event: NavigationEnd) => { | ||||||
| @@ -44,8 +60,4 @@ export class AppComponent implements OnInit { | |||||||
|       this.user = user; |       this.user = user; | ||||||
|     }); |     }); | ||||||
|   } |   } | ||||||
|  |  | ||||||
|   login() { |  | ||||||
|     this.dialog.open(LoginComponent); |  | ||||||
|   } |  | ||||||
| } | } | ||||||
|   | |||||||
| @@ -3,6 +3,14 @@ | |||||||
|         <div class="row"> |         <div class="row"> | ||||||
|             <div class="col-12 py-4"> |             <div class="col-12 py-4"> | ||||||
|                 <img [src]="product.image" class="float-left img-fluid mb-4 mr-4"> |                 <img [src]="product.image" class="float-left img-fluid mb-4 mr-4"> | ||||||
|  |                 <div class="float-right"> | ||||||
|  |                     <mat-form-field class="mr-1" style="width: 40px"> | ||||||
|  |                         <input #quantity matInput type="number" value="1" min="1"> | ||||||
|  |                     </mat-form-field> | ||||||
|  |                     <button mat-raised-button color="primary" (click)="app.addToCart(product.id, product.name, product.price, quantity.value)"> | ||||||
|  |                         <mat-icon>add_shopping_cart</mat-icon> Buy | ||||||
|  |                     </button> | ||||||
|  |                 </div> | ||||||
|                 <h2 class="roboto">{{product.name}}</h2> |                 <h2 class="roboto">{{product.name}}</h2> | ||||||
|                 <h5 *ngIf="product.price" class="text-muted">{{product.price | currency}}</h5> |                 <h5 *ngIf="product.price" class="text-muted">{{product.price | currency}}</h5> | ||||||
|                 <h5 *ngIf="!product.price" class="text-muted">Contact For Price</h5> |                 <h5 *ngIf="!product.price" class="text-muted">Contact For Price</h5> | ||||||
|   | |||||||
| @@ -1,7 +1,9 @@ | |||||||
| import {Component} from '@angular/core'; | import {Component} from '@angular/core'; | ||||||
| import {AngularFirestore} from '../../../../node_modules/angularfire2/firestore'; | import {AngularFirestore} from 'angularfire2/firestore'; | ||||||
| import {ActivatedRoute} from '../../../../node_modules/@angular/router'; | import {ActivatedRoute} from '@angular/router'; | ||||||
| import {DomSanitizer} from '../../../../node_modules/@angular/platform-browser'; | import {DomSanitizer} from 'node_modules/@angular/platform-browser'; | ||||||
|  | import {AppComponent} from '../../app.component'; | ||||||
|  | import {map} from 'rxjs/operators'; | ||||||
|  |  | ||||||
| @Component({ | @Component({ | ||||||
|   selector: 'products', |   selector: 'products', | ||||||
| @@ -10,19 +12,31 @@ import {DomSanitizer} from '../../../../node_modules/@angular/platform-browser'; | |||||||
| export class ProductsComponent { | export class ProductsComponent { | ||||||
|   product; |   product; | ||||||
|  |  | ||||||
|   constructor(private route: ActivatedRoute, private db: AngularFirestore, private domSanitizer: DomSanitizer) {} |   constructor( | ||||||
|  |     private route: ActivatedRoute, | ||||||
|  |     private db: AngularFirestore, | ||||||
|  |     private domSanitizer: DomSanitizer, | ||||||
|  |     public app: AppComponent | ||||||
|  |   ) {} | ||||||
|  |  | ||||||
|   ngOnInit() { |   ngOnInit() { | ||||||
|     this.route.params.subscribe(params => { |     this.route.params.subscribe(params => { | ||||||
|       this.db |       this.db | ||||||
|         .collection('products', ref => ref.where('name', '==', params['product'])) |         .collection('products', ref => ref.where('name', '==', params['product'])) | ||||||
|         .valueChanges() |         .snapshotChanges() | ||||||
|  |         .pipe( | ||||||
|  |           map(rows => | ||||||
|  |             rows.map((row: any) => Object.assign({id: row.payload.doc.id}, row.payload.doc.data())).map((row: any) => { | ||||||
|  |               row.image = this.domSanitizer.bypassSecurityTrustUrl(row.image); | ||||||
|  |               row.description = this.domSanitizer.bypassSecurityTrustHtml( | ||||||
|  |                 row.description.replace(/(\r\n|\r|\n)/g, '<br>') | ||||||
|  |               ); | ||||||
|  |               return row; | ||||||
|  |             }) | ||||||
|  |           ) | ||||||
|  |         ) | ||||||
|         .subscribe(data => { |         .subscribe(data => { | ||||||
|           this.product = data[0]; |           this.product = data[0]; | ||||||
|           this.product.image = this.domSanitizer.bypassSecurityTrustUrl(this.product.image); |  | ||||||
|           this.product.description = this.domSanitizer.bypassSecurityTrustHtml( |  | ||||||
|             this.product.description.replace(/(\r\n|\r|\n)/g, '<br>') |  | ||||||
|           ); |  | ||||||
|         }); |         }); | ||||||
|     }); |     }); | ||||||
|   } |   } | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user