diff --git a/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.html b/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.html
new file mode 100644
index 0000000..83e779b
--- /dev/null
+++ b/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.html
@@ -0,0 +1,7 @@
+
+
+
+
diff --git a/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.scss b/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.scss
new file mode 100644
index 0000000..8120eb3
--- /dev/null
+++ b/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.scss
@@ -0,0 +1,20 @@
+.password-input {
+ padding: 0;
+ color: #696969;
+ position: relative;
+ display: flex;
+ align-items: center;
+
+ input {
+ border: none;
+ padding-left: 35px;
+ text-align: center;
+ }
+
+ .password-eye {
+ position: absolute;
+ flex: 1 1 auto;
+ cursor: pointer;
+ }
+}
+
diff --git a/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.spec.ts b/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.spec.ts
new file mode 100644
index 0000000..da706fb
--- /dev/null
+++ b/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.spec.ts
@@ -0,0 +1,48 @@
+import { async, ComponentFixture, TestBed } from '@angular/core/testing';
+
+import { PasswordInputComponent } from './password-input.component';
+import { FormsModule, ReactiveFormsModule } from '@angular/forms';
+
+describe('Component: PasswordInputComponent', () => {
+ let component: PasswordInputComponent;
+ let fixture: ComponentFixture;
+ let element: any;
+
+ beforeEach(async(() => {
+ TestBed.configureTestingModule({
+ imports: [FormsModule, ReactiveFormsModule],
+ declarations: [PasswordInputComponent]
+ }).compileComponents();
+ }));
+
+ beforeEach(() => {
+ fixture = TestBed.createComponent(PasswordInputComponent);
+ component = fixture.componentInstance;
+ element = fixture.nativeElement;
+ fixture.detectChanges();
+ });
+
+ it('should change input type with a click on the icon', () => {
+ expect(element.querySelector('input').type).toBe('password');
+
+ element.querySelector('i').click();
+ fixture.detectChanges();
+ expect(element.querySelector('input').type).toBe('text');
+
+ element.querySelector('i').click();
+ fixture.detectChanges();
+ expect(element.querySelector('input').type).toBe('password');
+ });
+
+ it('should change an icon with a click on it', () => {
+ expect(element.querySelector('i').classList).toContain('fa-eye');
+
+ element.querySelector('i').click();
+ fixture.detectChanges();
+ expect(element.querySelector('i').classList).toContain('fa-eye-slash');
+
+ element.querySelector('i').click();
+ fixture.detectChanges();
+ expect(element.querySelector('i').classList).toContain('fa-eye');
+ });
+});
diff --git a/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.ts b/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.ts
new file mode 100644
index 0000000..ae8b279
--- /dev/null
+++ b/projects/ng-rocketparts/src/lib/components/password-input/password-input.component.ts
@@ -0,0 +1,93 @@
+import {
+ Component,
+ ElementRef,
+ forwardRef,
+ HostBinding,
+ Input,
+ OnInit
+} from '@angular/core';
+import { ControlValueAccessor, NG_VALUE_ACCESSOR } from '@angular/forms';
+
+export const PASSWORD_INPUT_VALUE_ACCESSOR: any = {
+ provide: NG_VALUE_ACCESSOR,
+ useExisting: forwardRef(() => PasswordInputComponent), // tslint:disable-line
+ multi: true
+};
+
+@Component({
+ selector: 'ngr-password-input',
+ templateUrl: './password-input.component.html',
+ styleUrls: ['./password-input.component.scss'],
+ providers: [PASSWORD_INPUT_VALUE_ACCESSOR]
+})
+export class PasswordInputComponent implements OnInit, ControlValueAccessor {
+ @HostBinding('class.ngr-password-input')
+ passwordInputClass = true;
+
+ @Input()
+ placeholder: string;
+
+ @Input()
+ paddingLeft: number;
+
+ onChange: () => void;
+
+ onTouched: () => void;
+
+ input: any;
+
+ displayValue: string;
+
+ disabled: boolean;
+
+ show: boolean;
+
+ constructor(private elem: ElementRef) {}
+
+ ngOnInit() {
+ this.input = this.elem.nativeElement.querySelector('input');
+ this.show = this.input.type === 'password';
+ }
+
+ registerOnChange(fn: any): void {
+ this.onChange = () => {
+ if (fn) {
+ fn(this.displayValue);
+ }
+ };
+ }
+
+ registerOnTouched(fn: any): void {
+ this.onTouched = fn;
+ }
+
+ setDisabledState(isDisabled: boolean): void {
+ this.disabled = isDisabled;
+ }
+
+ writeValue(value: any): void {
+ if (this.displayValue !== value) {
+ this.displayValue = value;
+ }
+ }
+
+ /**
+ * Called when the selection changed
+ * @param value
+ */
+ onInputChange(value: string) {
+ this.displayValue = value;
+ if (this.onChange) {
+ this.onChange();
+ }
+ }
+
+ /**
+ * Allows to show and hide password
+ * @param {Event} e
+ */
+ toggle(e: Event) {
+ this.show = !this.show;
+ this.input.type = this.input.type === 'password' ? 'text' : 'password';
+ }
+}
diff --git a/projects/ng-rocketparts/src/lib/components/password-input/password-input.module.spec.ts b/projects/ng-rocketparts/src/lib/components/password-input/password-input.module.spec.ts
new file mode 100644
index 0000000..51b30a9
--- /dev/null
+++ b/projects/ng-rocketparts/src/lib/components/password-input/password-input.module.spec.ts
@@ -0,0 +1,13 @@
+import { PasswordInputModule } from './password-input.module';
+
+describe('PasswordInputModule', () => {
+ let passwordInputModule: PasswordInputModule;
+
+ beforeEach(() => {
+ passwordInputModule = new PasswordInputModule();
+ });
+
+ it('should create an instance', () => {
+ expect(passwordInputModule).toBeTruthy();
+ });
+});
diff --git a/projects/ng-rocketparts/src/lib/components/password-input/password-input.module.ts b/projects/ng-rocketparts/src/lib/components/password-input/password-input.module.ts
new file mode 100644
index 0000000..bba4b41
--- /dev/null
+++ b/projects/ng-rocketparts/src/lib/components/password-input/password-input.module.ts
@@ -0,0 +1,11 @@
+import { NgModule } from '@angular/core';
+import { CommonModule } from '@angular/common';
+import { FormsModule, ReactiveFormsModule } from '@angular/forms';
+import { PasswordInputComponent } from './password-input.component';
+
+@NgModule({
+ imports: [CommonModule, FormsModule, ReactiveFormsModule],
+ declarations: [PasswordInputComponent],
+ exports: [PasswordInputComponent]
+})
+export class PasswordInputModule {}
diff --git a/projects/ng-rocketparts/src/lib/ng-rocketparts.module.ts b/projects/ng-rocketparts/src/lib/ng-rocketparts.module.ts
index 7944e05..97e301e 100644
--- a/projects/ng-rocketparts/src/lib/ng-rocketparts.module.ts
+++ b/projects/ng-rocketparts/src/lib/ng-rocketparts.module.ts
@@ -1,9 +1,14 @@
import { NgModule } from '@angular/core';
import { MaybeAsyncPipe } from './pipes/maybe-async.pipe';
+import { PasswordInputModule } from './components/password-input/password-input.module';
+import { CommonModule } from '@angular/common';
+import { FormsModule, ReactiveFormsModule } from '@angular/forms';
+
+const MODULES = [PasswordInputModule];
@NgModule({
- imports: [],
+ imports: [CommonModule, FormsModule, ReactiveFormsModule],
declarations: [MaybeAsyncPipe],
- exports: [MaybeAsyncPipe]
+ exports: [...MODULES, MaybeAsyncPipe]
})
export class NgRocketPartsModule {}