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

1 start #20

Open
wants to merge 15 commits into
base: 1-start
Choose a base branch
from
3 changes: 2 additions & 1 deletion src/app/app-routing.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import {CourseComponent} from './course/course.component';
import {courseResolver} from './services/course.resolver';
import {LoginComponent} from './login/login.component';
import {CreateCourseComponent} from './create-course/create-course.component';
import { LoginReactiveComponent } from './login-reactive/login-reactive.component';

const routes: Routes = [
{
Expand All @@ -30,7 +31,7 @@ const routes: Routes = [
},
{
path: 'login',
component: LoginComponent
component: LoginReactiveComponent
},
{
path: '**',
Expand Down
2 changes: 1 addition & 1 deletion src/app/app.component.css
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@

>>> body {
body {
margin: 0;
}

Expand Down
8 changes: 6 additions & 2 deletions src/app/app.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ import { MatToolbarModule } from "@angular/material/toolbar";
import {CoursesService} from "./services/courses.service";
import { provideHttpClient, withInterceptorsFromDi } from "@angular/common/http";
import { CourseDialogComponent } from './course-dialog/course-dialog.component';
import {FormsModule, ReactiveFormsModule} from '@angular/forms';
import {FormGroup, FormsModule, ReactiveFormsModule} from '@angular/forms';
import {LoginComponent} from './login/login.component';
import { CreateCourseComponent } from './create-course/create-course.component';
import {MatNativeDateModule} from '@angular/material/core';
Expand All @@ -41,6 +41,8 @@ import {CreateCourseStep1Component} from './create-course/create-course-step-1/c
import {FileUploadComponent} from './file-upload/file-upload.component';
import {MatProgressBarModule} from '@angular/material/progress-bar';
import {LoginReactiveComponent} from './login-reactive/login-reactive.component';
import { PasswordStrengthDirective } from './directives/password-strength.directive';
import { OnlyOneErrorPipe } from './pipes/only-one-error.pipe';

@NgModule({ declarations: [
AppComponent,
Expand All @@ -56,7 +58,9 @@ import {LoginReactiveComponent} from './login-reactive/login-reactive.component'
CreateCourseStep3Component,
AddressFormComponent,
FileUploadComponent,
LoginReactiveComponent
LoginReactiveComponent,
PasswordStrengthDirective,
OnlyOneErrorPipe
],
bootstrap: [AppComponent], imports: [BrowserModule,
BrowserAnimationsModule,
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<div [formGroup]="form">

<mat-form-field>

<input matInput placeholder="Course title" formControlName="title" #title >

<mat-hint align="end">
{{title.value.length}} / 60
</mat-hint>

</mat-form-field>

</div>
Original file line number Diff line number Diff line change
@@ -1,18 +1,23 @@
import {Component, OnInit} from '@angular/core';
import {FormBuilder, FormGroup, Validators} from '@angular/forms';
import {CoursesService} from '../../services/courses.service';
import {Observable} from 'rxjs';
import {filter} from 'rxjs/operators';
import { Component, OnInit } from "@angular/core";
import { FormBuilder, FormGroup, Validators } from "@angular/forms";
import { CoursesService } from "../../services/courses.service";
import { Observable } from "rxjs";
import { filter } from "rxjs/operators";

@Component({
selector: 'create-course-step-1',
templateUrl: './create-course-step-1.component.html',
styleUrls: ['./create-course-step-1.component.scss']
selector: "create-course-step-1",
templateUrl: "./create-course-step-1.component.html",
styleUrls: ["./create-course-step-1.component.scss"],
})
export class CreateCourseStep1Component implements OnInit {
form = this.fb.group({
title: [
"",
[Validators.required, Validators.minLength(5), Validators.maxLength(60)],
],
});

ngOnInit() {

}
constructor(private fb: FormBuilder) {}

ngOnInit() {}
}
15 changes: 12 additions & 3 deletions src/app/create-course/create-course.component.html
Original file line number Diff line number Diff line change
@@ -1,8 +1,17 @@

<div class="create-course-panel data-form">

<h2 class="title">Create New Course</h2>

</div>
<mat-horizontal-stepper class="mat-elevation-z5" labelPosition="bottom">
<mat-step>
<ng-template matStepLabel>course landing page details</ng-template>

<create-course-step-1></create-course-step-1>

<div class="stepper-buttons">
<button mat-raised-button color="primary" matStepperNext>
Continue to Step 2
</button>
</div>
</mat-step>
</mat-horizontal-stepper>
</div>
21 changes: 21 additions & 0 deletions src/app/directives/password-strength.directive.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import { Directive } from "@angular/core";
import { AbstractControl, NG_VALIDATORS, ValidationErrors, Validator, Validators } from "@angular/forms";
import { createPasswordStrengthValidator } from "../validators/password-strength.validator";


@Directive({
selector: '[passwordStrength]',
providers: [{
provide: NG_VALIDATORS,
useExisting: PasswordStrengthDirective,
multi: true
}]


})
export class PasswordStrengthDirective implements Validator {

validate(control: AbstractControl): ValidationErrors | null{
return createPasswordStrengthValidator()(control);
}
}
5 changes: 5 additions & 0 deletions src/app/login-reactive/login-reactive.component.css
Original file line number Diff line number Diff line change
Expand Up @@ -14,5 +14,10 @@
border-bottom: 1px solid grey;
margin-bottom: 10px;
}
.field-message {
color: red; /* Example styling */
font-size: 12px;
margin-top: 5px;
}


57 changes: 49 additions & 8 deletions src/app/login-reactive/login-reactive.component.html
Original file line number Diff line number Diff line change
@@ -1,27 +1,68 @@
<mat-card class="login-page">
<mat-card-title>Login (Reactive)</mat-card-title>
<mat-card-content>

<form class="login-form data-form">

<form class="login-form data-form" [formGroup]="form">
<mat-form-field>
<input
matInput
type="email"
name="email"
placeholder="Email"
formControlName="email"
/>

<input matInput type="email" name="email"
placeholder="Email">
<mat-error *ngIf="email.errors?.required"
>The email is mandatory.</mat-error
>

<mat-error *ngIf="email.errors?.minlength">
Your email must have minimum
{{ email.errors?.minlength.requiredLength }} chars, but it only has
{{ email.errors?.minlength.actualLength }}.
</mat-error>

<mat-error *ngIf="email.errors?.email"
>The email is not a valid email.</mat-error
>
</mat-form-field>

<mat-form-field>
<input
matInput
type="password"
placeholder="Password"
formControlName="password"
/>

<input matInput type="password" placeholder="Password">

<mat-error *ngIf="password.errors?.required"
>The password is mandatory</mat-error
>
</mat-form-field>

<button mat-raised-button color="primary">
<ng-container
*ngIf="password.errors | onlyOneError : ['passwordStrength'] as error"
>
<div class="field-message" *ngIf="error.passwordStrength">
Your password must have lower case, upper case and numeric characters.
</div>
</ng-container>

<button mat-raised-button color="primary" [disabled]="!form.valid">
Login
</button>

<button mat-raised-button color="primary" (click)="reset()">
Reset
</button>

</form>

<div class="form-val">
{{ form.value | json }}
</div>

<div class="form-val">
{{ form.valid | json }}
</div>
</mat-card-content>
</mat-card>
55 changes: 44 additions & 11 deletions src/app/login-reactive/login-reactive.component.ts
Original file line number Diff line number Diff line change
@@ -1,21 +1,54 @@
import { Component, OnInit } from '@angular/core';

import { Component, OnInit } from "@angular/core";
import {
FormBuilder,
FormControl,
FormGroup,
NonNullableFormBuilder,
Validators,
} from "@angular/forms";
import { createPasswordStrengthValidator } from "../validators/password-strength.validator";

@Component({
selector: 'login',
templateUrl: './login-reactive.component.html',
styleUrls: ['./login-reactive.component.css']
selector: "login",
templateUrl: "./login-reactive.component.html",
styleUrls: ["./login-reactive.component.css"],
})
export class LoginReactiveComponent implements OnInit {
form = this.fb.group({
email: [
"",
{
validators: [Validators.required, Validators.email],
updateOn: "blur",
},
],
password: [
"",
[
Validators.required,
Validators.minLength(8),
createPasswordStrengthValidator(),
],
],
});

constructor(private fb: NonNullableFormBuilder) {}

ngOnInit() {}

get email() {
return this.form.controls["email"];
}


constructor() {


get password() {
return this.form.controls["password"];
}

ngOnInit() {
login() {}

}
reset() {
this.form.reset();

console.log(this.form.value);
}
}
6 changes: 6 additions & 0 deletions src/app/login/login.component.css
Original file line number Diff line number Diff line change
Expand Up @@ -15,4 +15,10 @@
margin-bottom: 10px;
}

.field-message {
color: red; /* Example styling */
font-size: 12px;
margin-top: 5px;
}


70 changes: 58 additions & 12 deletions src/app/login/login.component.html
Original file line number Diff line number Diff line change
@@ -1,27 +1,73 @@
<mat-card class="login-page">
<mat-card-title>Login</mat-card-title>
<mat-card-title>Login (Template-Driven-Form)</mat-card-title>
<mat-card-content>

<form class="login-form data-form">

<form
class="login-form data-form"
#loginForm="ngForm"
(submit)="login(loginForm)"
>
<mat-form-field>
<input
matInput
type="email"
name="email"
ngModel
#email="ngModel"
required
email
minlength="3"
maxlength="20"
placeholder="Email"
/>

<input matInput type="email" name="email"
placeholder="Email">
<mat-error *ngIf="email.errors?.required"
>The email is mandatory.</mat-error
>

<mat-error *ngIf="email.errors?.minlength">
Your email must have minimum
{{ email.errors?.minlength.requiredLength }} chars, but it only has
{{ email.errors?.minlength.actualLength }}.
</mat-error>

<mat-error *ngIf="email.errors?.email"
>The email is not a valid email.</mat-error
>
</mat-form-field>

<mat-form-field>

<input matInput type="password" placeholder="Password">

<input
matInput
type="password"
name="password"
ngModel
#password="ngModel"
required
passwordStrength
placeholder="Password"
/>
<mat-error *ngIf="password.errors?.required"
>The password is mandatory</mat-error
>
</mat-form-field>
<ng-container
*ngIf="password.errors | onlyOneError : ['passwordStrength'] as error"
>
<div class="field-message" *ngIf="error.passwordStrength"
>Your password must have lower case, upper case and numeric
characters.</div
>
</ng-container>

<button mat-raised-button color="primary">
<button
mat-raised-button
color="primary"
(click)="login(loginForm)"
type="submit"
[disabled]="!loginForm.valid"
>
Login
</button>

</form>

</mat-card-content>
</mat-card>
Loading