NGX-AWESOME-UPLOADER
This is an Angular Library for uploading files. It supports: File Upload and Preview (additionally preview images with lightbox), validation, image cropper , drag and drop with multi language support.
Tested on Angular Angular 6+. Supports Server Side Rendering.
Breaking Changes: Check Changes changes if you come from version < 10.
Quick-links
Example Application or
StackBlitzDemo
Install
npm install ngx-awesome-uploader --save
Load the module for your app:
import { FilePickerModule } from 'ngx-awesome-uploader';
@NgModule({
imports: [
...
FilePickerModule
]
})
Usage
In order to make library maximum compatible with apis you need to create and provide
custom adapter which implements upload and remove requests. That's because I have no idea how to get file id in upload response json :) .
So this libray exposes a FilePickerAdapter abstract class which you can import on your new class file definition:
import { FilePickerAdapter } from 'ngx-awesome-uploader';
After importing it to your custom adapter implementation (EG: CustomAdapter.ts), you must implement those 2 methods which are abstract in the FilePickerAdapter base class which are:
public abstract uploadFile(fileItem: FilePreviewModel): Observable<UploadResponse>;
public abstract removeFile(fileItem: FilePreviewModel): Observable<any>;
You can check DEMO adapter here
Now you can use it in your template
<ngx-awesome-uploader
[adapter]="adapter"
>
</ngx-awesome-uploader>
and in the Component:
import { HttpClient } from '@angular/common/http';
import { DemoFilePickerAdapter } from './demo-file-picker.adapter';
import { Component} from '@angular/core';
@Component({
selector: 'demo-file-picker',
templateUrl: './demo-file-picker.component.html',
styleUrls: ['./demo-file-picker.component.scss']
})
export class DemoFilePickerComponent {
adapter = new DemoFilePickerAdapter(this.http);
constructor(private http: HttpClient) { }
}
Note: As you see you should provide http instance to adapter.
Still in Doubt? Check Minimal Setup Demo
API
@Input() enableCropper = false;
@Input() showeDragDropZone = true;
@Input() uploadType = 'multi';
@Input() fileMaxSize: number;
@Input() fileMaxCount: number;
@Input() totalMaxSize: number;
@Input() accept: string;
@Input() fileExtensions: String;
@Input() cropperOptions: Object;
@Input() adapter: FilePickerAdapter;
@Input() dropzoneTemplate: TemplateRef<any>;
@Input() itemTemplate: TemplateRef<any>;
@Input() showPreviewContainer = true;
@Input() customValidator: (file: File) => Observable<boolean>;
@Input() captions: UploaderCaptions;
@Input() enableAutoUpload = true;
@Input() fileInputCapture: string;
Output events
@Output() uploadSuccess = new EventEmitter<FilePreviewModel>();
@Output() uploadFail = new EventEmitter<HttpErrorResponse>();
@Output() removeSuccess = new EventEmitter<FilePreviewModel>();
@Output() validationError = new EventEmitter<ValidationError>();
@Output() fileAdded = new EventEmitter<FilePreviewModel>();
@Output() fileRemoved = new EventEmitter<FilePreviewModel>();
File-Validation
Built-in-validations
All validations are emitted through ValidationError event.
To listen to validation errors (in case you provided validations), validationError event is emitted. validationError event implements interface ValidationError
and which emits failed file and error type.
Supported validations:
Validation Type | Description | Default |
---|
fileMaxSize: number | Max size of selected file in MB. | No limit |
fileExtensions: String | Emitted when file does not satisfy provided extension | Any extension |
uploadType: String | Upload type. Values: 'single' and 'multi'. | multi |
totalMaxSize: number | Total Max size of files in MB. If cropper is enabled, the cropped image size is considered. | No limit |
fileMaxCount: number | Limit total files to upload by count | No limit |
Custom-validation
You can also provide your own custom validation along with built-in validations.
You custom validation takes file: File
and returns Observable<boolean>
;
So that means you can provide sync and async validations.
public myCustomValidator(file: File): Observable<boolean> {
if (file.name.includes('panda')) {
return of(true);
}
if (file.size > 50) {
return this.http.get('url').pipe(map((res) => res === 'OK' ));
}
return of(false);
}
and pass to Template:
<ngx-awesome-uploader
[customValidator]="myCustomValidator"
>
</ngx-awesome-uploader>
Check Demo
Cropper
Library uses cropperjs to crop images but you need import it to use it. Example: in index html
<script src="https://cdnjs.cloudflare.com/ajax/libs/cropperjs/1.4.3/cropper.min.js" async> </script>
<link rel="stylesheet" href="https://cdnjs.cloudflare.com/ajax/libs/cropperjs/1.4.3/cropper.css" />
Note: To use cropper, you should set enableCropper to true. Look at API section above.
You can also provide your custom cropper options.
Custom-Template
You can provide custom template to library.
I) To provide custom template for drag and drop zone, use content projection. Example:
<ngx-awesome-uploader
[adapter]="adapter">
<div class="dropzoneTemplate">
<button>Custom</button>
</div>
</ngx-awesome-uploader>
Note: The wrapper of your custom template must have a class dropzoneTemplate.
Checkout Demo
II) To use custom file preview template, pass your custom template as below:
<ngx-awesome-uploader #uploader
[adapter]="adapter"
[itemTemplate]="itemTemplate"
>
</ngx-awesome-uploader>
<ng-template #itemTemplate let-fileItem="fileItem" let-uploadProgress="uploadProgress">
<p>{{fileItem.file.size}}</p>
<p>{{fileItem.fileName}}</p>
<p *ngIf="uploadProgress < 100">{{uploadProgress}}%</p>
<button (click)="uploader.removeFile(fileItem)">Remove</button>
</ng-template>
In custom template uploadProgress and fileItem (which implements FilePrevieModel interface) are exposed .
Multi Language
You can add multi language support for library by providing captions object (which implements UploaderCaptions interface).
Check Demo
Edit Mode
You can show your files without uploading them
@ViewChild('uploader', { static: true }) uploader: FilePickerComponent;
public ngOnInit(): void {
const files = [
{
fileName: 'My File 1 for edit.png'
},
{
fileName: 'My File 2 for edit.xlsx'
}
] as FilePreviewModel[];
this.uploader.setFiles(files);
}
Bonus
You can also check out library router animations
Contribution
You can fork project from github. Pull requests are kindly accepted.
-
Building library: ng build file-picker --prod
-
Running tests: ng test file-picker --browsers=ChromeHeadless
-
Run demo: ng serve