1. 安装依赖
复制
2. 创建组件 名为 cropper-img
| ng g c /pages/component/cropper-img --module=app |
复制
3. cropper-img.component.html
文件
| <div class="cropper-img"> |
| <label for="btn" class="upload-btn" >上传需要被裁剪的图片(裁剪宽高比:{{width}} / {{height}})</label> |
| <input id="btn" #imageInput accept=".jpg,.png,.jpeg" type="file" style="display: none;" (change)="imageChangeEvent($event)"> |
| <div class="copperArea"> |
| <div class="leftCopper"> |
| <img #imgCropper class="cropperMain" /> |
| </div> |
| <div class="rightPreview"> |
| <div> |
| <div class="liTitle">预览</div> |
| <img class="preImg" [src]="croppedImage" /> |
| </div> |
| |
| <div> |
| <div class="liTitle">工具</div> |
| <div class="toolArea "> |
| <div class="J_KnowBtn btnTheme" (click)="rotateImage()">旋转图片</div> |
| <div class="J_KnowBtn btnTheme" (click)="sureCropper()">确认裁剪</div> |
| </div> |
| </div> |
| </div> |
| </div> |
| </div> |
复制
4. cropper-img.component.less
文件
复制
| .cropper-img { |
| .copperArea { |
| display: flex; |
| justify-content: space-between; |
| .leftCopper { |
| width: 400px; |
| height: 300px; |
| .cropperMain { |
| width: 100%; |
| height: 100%; |
| border: solid 1px #000000; |
| } |
| } |
| .rightPreview { |
| width: 230px; |
| height: 300px; |
| .preImg { |
| width: 200px; |
| border-radius: 10px; |
| border: solid 1px #000000; |
| } |
| .toolArea { |
| display: flex; |
| justify-content: flex-start; |
| align-items: center; |
| .J_KnowBtn { |
| width: 100px; |
| height: 30px; |
| border-radius: 5px; |
| color: #ffffff; |
| font-size: 14px; |
| font-weight: 600; |
| margin-right: 10px; |
| background: #00d7c6; |
| text-align: center; |
| line-height: 30px; |
| &:last-child { |
| margin-right: 0; |
| } |
| } |
| } |
| } |
| } |
| .liTitle { |
| font-size: 18px; |
| font-weight: 600; |
| color: #000000; |
| } |
| input { |
| width: 100%; |
| height: 30px; |
| border-radius: 5px; |
| border: solid 1px #00d7c6; |
| color: #00d7c6; |
| font-size: 14px; |
| font-weight: 600; |
| margin-left: 10px; |
| } |
| .upload-btn { |
| height: 30px; |
| line-height: 30px; |
| padding: 0 20px; |
| background-color: #00d7c6; |
| color: #ffffff; |
| text-align: center; |
| display: inline-block; |
| border-radius: 4px; |
| } |
| } |
| |
复制
5. cropper-img.component.ts
文件
| import { Component, ElementRef, EventEmitter, Input, OnInit, Output, ViewChild, ViewEncapsulation } from '@angular/core'; |
| import { ApiService } from '../../service/api/api.service'; |
| import { RequestService } from '../../service/request/request.service'; |
| import Cropper from '../../../assets/cropperjs/cropper.min.js'; |
| import { NzMessageService } from 'ng-zorro-antd/message'; |
| @Component({ |
| selector: 'app-cropper-img', |
| templateUrl: './cropper-img.component.html', |
| styleUrls: ['./cropper-img.component.less','../../../assets/cropperjs/cropper.min.css'], |
| encapsulation:ViewEncapsulation.None |
| }) |
| export class CropperImgComponent implements OnInit { |
| @Input () width ; |
| @Input () height ; |
| @Input () imgUrl ; |
| @Output () getImgUrl: EventEmitter<boolean> = new EventEmitter(); |
| |
| @ViewChild('imageInput') imgInput:ElementRef; |
| @ViewChild('imgCropper') imgCropper:ElementRef; |
| myCropper: any; |
| croppedImage: any = ''; |
| nowRotate=0; |
| |
| constructor( |
| private res:RequestService, |
| private message : NzMessageService |
| ) { |
| setTimeout(() => { |
| this.imgCropper.nativeElement.src=this.imgUrl; |
| this.iniCropper() |
| }, 0); |
| } |
| |
| imageChangeEvent(event: any): void { |
| |
| const fr = new FileReader(); |
| fr.readAsDataURL(event.path[0].files[0]); |
| fr.onload = ()=>{ |
| this.imgCropper.nativeElement.src=fr.result; |
| this.iniCropper(); |
| }; |
| } |
| iniCropper() { |
| this.myCropper = new Cropper(this.imgCropper.nativeElement, { |
| aspectRatio: (this.width&&this.height)? this.width / this.height : 'auto', |
| dragMode : 'move', |
| viewMode : 1, |
| autoCropArea : 1, |
| |
| |
| crop:event=> { |
| this.croppedImage= this.myCropper.getCroppedCanvas({ |
| imageSmoothingQuality: 'high' |
| }).toDataURL('image/png') |
| }, |
| replace:event =>{ |
| if(this.imgUrl){ |
| this.myCropper.replace(this.imgUrl) |
| } |
| } |
| }); |
| this.myCropper.replace(this.imgCropper.nativeElement.src) |
| } |
| rotateImage(){ |
| this.nowRotate+=90; |
| this.myCropper.rotateTo(this.nowRotate) |
| } |
| sureCropper(){ |
| |
| |
| this.uploadImg() |
| this.imgInput.nativeElement.value=""; |
| |
| } |
| base64toFile() { |
| let base = this.croppedImage |
| var arr = base.split(','), mime = arr[0].match(/:(.*?);/)[1], |
| bstr = atob(arr[1]), n = bstr.length, u8arr = new Uint8Array(n); |
| while(n--){ |
| u8arr[n] = bstr.charCodeAt(n); |
| } |
| let filename = new Date().getTime() |
| return new File([u8arr], filename+".png", {type:mime}); |
| } |
| uploadImg(){ |
| const formData = new FormData(); |
| let file = this.base64toFile() |
| formData.append('file', file) |
| formData.append('type', '3') |
| this.res.post(ApiService.common_post_commonFileUpload,formData).subscribe(res=>{ |
| this.message.success('上传成功') |
| |
| this.getImgUrl.emit(res.data); |
| }) |
| } |
| ngOnInit(): void { |
| |
| } |
| } |
| |
复制
6.使用方式
| |
| <app-cropper-img |
| [width]="cropperWidth" |
| [height]="cropperHeight" |
| [imgUrl]="validateForm.value.coverUrl" |
| (getImgUrl)="getImgUrl($event)" |
| ></app-cropper-img> |
复制
| |
| cropperWidth : number = 64; |
| cropperHeight : number = 64; |
| coverUrl : string = ''; |
| getImgUrl(e){ |
| this.coverUrl : e.absolutePath |
| } |
复制
注:如果npm
引入的cropper
不能使用,到这里下载 【cropperjs】静态资源引入项目中。
复制