@cropvue/vue 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,304 @@
1
+ import type { CropResult, CropVueError, StencilType, OutputFormat, UploadFn, QueueItem } from '@cropvue/core';
2
+ type __VLS_Props = {
3
+ stencil?: StencilType;
4
+ aspectRatio?: number | null;
5
+ minWidth?: number;
6
+ minHeight?: number;
7
+ maxWidth?: number;
8
+ maxHeight?: number;
9
+ outputFormat?: OutputFormat;
10
+ outputQuality?: number;
11
+ outputMaxWidth?: number;
12
+ outputMaxHeight?: number;
13
+ accept?: string[];
14
+ maxFileSize?: number;
15
+ multiple?: boolean;
16
+ upload?: UploadFn | null;
17
+ src?: string | null;
18
+ modelValue?: CropResult | null;
19
+ pannable?: boolean;
20
+ };
21
+ type Phase = 'dropzone' | 'editor' | 'done';
22
+ declare function confirm(): Promise<void>;
23
+ declare function cancel(): void;
24
+ declare function restart(): void;
25
+ declare function remove(): void;
26
+ declare function reedit(): void;
27
+ declare var __VLS_1: {
28
+ open: () => void;
29
+ isDragging: boolean;
30
+ }, __VLS_3: {
31
+ open: () => void;
32
+ isDragging: boolean;
33
+ }, __VLS_5: {
34
+ image: import("@cropvue/core").ImageData | null;
35
+ transform: import("@cropvue/core").TransformState;
36
+ crop: import("@cropvue/core").CropState;
37
+ rotateLeft: () => void;
38
+ rotateRight: () => void;
39
+ flipX: () => void;
40
+ flipY: () => void;
41
+ zoomIn: () => void;
42
+ zoomOut: () => void;
43
+ reset: () => void;
44
+ confirm: typeof confirm;
45
+ cancel: typeof cancel;
46
+ remove: typeof remove;
47
+ pannable: boolean;
48
+ }, __VLS_15: {
49
+ rotateLeft: () => void;
50
+ rotateRight: () => void;
51
+ flipX: () => void;
52
+ flipY: () => void;
53
+ zoomIn: () => void;
54
+ zoomOut: () => void;
55
+ reset: () => void;
56
+ transform: import("@cropvue/core").TransformState;
57
+ }, __VLS_30: {
58
+ image: import("@cropvue/core").ImageData | null;
59
+ transform: import("@cropvue/core").TransformState;
60
+ crop: import("@cropvue/core").CropState;
61
+ }, __VLS_32: {
62
+ confirm: typeof confirm;
63
+ cancel: typeof cancel;
64
+ remove: typeof remove;
65
+ isUploading: boolean;
66
+ progress: number;
67
+ }, __VLS_34: {
68
+ result: {
69
+ blob: {
70
+ readonly size: number;
71
+ readonly type: string;
72
+ arrayBuffer: () => Promise<ArrayBuffer>;
73
+ bytes: () => Promise<Uint8Array<ArrayBuffer>>;
74
+ slice: (start?: number, end?: number, contentType?: string) => Blob;
75
+ stream: () => ReadableStream<Uint8Array<ArrayBuffer>>;
76
+ text: () => Promise<string>;
77
+ };
78
+ file: {
79
+ readonly lastModified: number;
80
+ readonly name: string;
81
+ readonly webkitRelativePath: string;
82
+ readonly size: number;
83
+ readonly type: string;
84
+ arrayBuffer: () => Promise<ArrayBuffer>;
85
+ bytes: () => Promise<Uint8Array<ArrayBuffer>>;
86
+ slice: (start?: number, end?: number, contentType?: string) => Blob;
87
+ stream: () => ReadableStream<Uint8Array<ArrayBuffer>>;
88
+ text: () => Promise<string>;
89
+ };
90
+ url: string;
91
+ coords: {
92
+ x: number;
93
+ y: number;
94
+ width: number;
95
+ height: number;
96
+ rotation: number;
97
+ flipX: boolean;
98
+ flipY: boolean;
99
+ scale: number;
100
+ };
101
+ width: number;
102
+ height: number;
103
+ originalWidth: number;
104
+ originalHeight: number;
105
+ } | null;
106
+ restart: typeof restart;
107
+ reedit: typeof reedit;
108
+ remove: typeof remove;
109
+ }, __VLS_36: {}, __VLS_38: {
110
+ progress: number;
111
+ };
112
+ type __VLS_Slots = {} & {
113
+ dropzone?: (props: typeof __VLS_1) => any;
114
+ } & {
115
+ 'dropzone-content'?: (props: typeof __VLS_3) => any;
116
+ } & {
117
+ editor?: (props: typeof __VLS_5) => any;
118
+ } & {
119
+ toolbar?: (props: typeof __VLS_15) => any;
120
+ } & {
121
+ preview?: (props: typeof __VLS_30) => any;
122
+ } & {
123
+ actions?: (props: typeof __VLS_32) => any;
124
+ } & {
125
+ done?: (props: typeof __VLS_34) => any;
126
+ } & {
127
+ error?: (props: typeof __VLS_36) => any;
128
+ } & {
129
+ loading?: (props: typeof __VLS_38) => any;
130
+ };
131
+ declare const __VLS_component: import("vue").DefineComponent<__VLS_Props, {
132
+ cropper: {
133
+ image: import("vue").Ref<import("@cropvue/core").ImageData | null, import("@cropvue/core").ImageData | null>;
134
+ transform: import("vue").Ref<import("@cropvue/core").TransformState, import("@cropvue/core").TransformState>;
135
+ crop: import("vue").Ref<import("@cropvue/core").CropState, import("@cropvue/core").CropState>;
136
+ isReady: import("vue").Ref<boolean, boolean>;
137
+ loadFile: (file: File) => Promise<void>;
138
+ loadUrl: (url: string) => Promise<void>;
139
+ rotateLeft: () => void;
140
+ rotateRight: () => void;
141
+ rotateTo: (degrees: number) => void;
142
+ flipX: () => void;
143
+ flipY: () => void;
144
+ zoomTo: (scale: number) => void;
145
+ zoomBy: (delta: number) => void;
146
+ panTo: (x: number, y: number) => void;
147
+ reset: () => void;
148
+ setCropArea: (area: Partial<import("@cropvue/core").CropState>) => void;
149
+ setStencil: (stencil: StencilType) => void;
150
+ setAspectRatio: (ratio: number | null) => void;
151
+ getResult: (opts?: {
152
+ format?: "auto" | "webp" | "jpeg" | "png";
153
+ quality?: number;
154
+ maxWidth?: number;
155
+ maxHeight?: number;
156
+ }) => Promise<CropResult>;
157
+ getPreviewUrl: () => string;
158
+ canvasRef: import("vue").Ref<HTMLCanvasElement | null, HTMLCanvasElement | null>;
159
+ renderToCanvas: () => void;
160
+ };
161
+ phase: import("vue").Ref<Phase, Phase>;
162
+ confirm: typeof confirm;
163
+ cancel: typeof cancel;
164
+ restart: typeof restart;
165
+ reedit: typeof reedit;
166
+ remove: typeof remove;
167
+ result: import("vue").Ref<{
168
+ blob: {
169
+ readonly size: number;
170
+ readonly type: string;
171
+ arrayBuffer: () => Promise<ArrayBuffer>;
172
+ bytes: () => Promise<Uint8Array<ArrayBuffer>>;
173
+ slice: (start?: number, end?: number, contentType?: string) => Blob;
174
+ stream: () => ReadableStream<Uint8Array<ArrayBuffer>>;
175
+ text: () => Promise<string>;
176
+ };
177
+ file: {
178
+ readonly lastModified: number;
179
+ readonly name: string;
180
+ readonly webkitRelativePath: string;
181
+ readonly size: number;
182
+ readonly type: string;
183
+ arrayBuffer: () => Promise<ArrayBuffer>;
184
+ bytes: () => Promise<Uint8Array<ArrayBuffer>>;
185
+ slice: (start?: number, end?: number, contentType?: string) => Blob;
186
+ stream: () => ReadableStream<Uint8Array<ArrayBuffer>>;
187
+ text: () => Promise<string>;
188
+ };
189
+ url: string;
190
+ coords: {
191
+ x: number;
192
+ y: number;
193
+ width: number;
194
+ height: number;
195
+ rotation: number;
196
+ flipX: boolean;
197
+ flipY: boolean;
198
+ scale: number;
199
+ };
200
+ width: number;
201
+ height: number;
202
+ originalWidth: number;
203
+ originalHeight: number;
204
+ } | null, CropResult | {
205
+ blob: {
206
+ readonly size: number;
207
+ readonly type: string;
208
+ arrayBuffer: () => Promise<ArrayBuffer>;
209
+ bytes: () => Promise<Uint8Array<ArrayBuffer>>;
210
+ slice: (start?: number, end?: number, contentType?: string) => Blob;
211
+ stream: () => ReadableStream<Uint8Array<ArrayBuffer>>;
212
+ text: () => Promise<string>;
213
+ };
214
+ file: {
215
+ readonly lastModified: number;
216
+ readonly name: string;
217
+ readonly webkitRelativePath: string;
218
+ readonly size: number;
219
+ readonly type: string;
220
+ arrayBuffer: () => Promise<ArrayBuffer>;
221
+ bytes: () => Promise<Uint8Array<ArrayBuffer>>;
222
+ slice: (start?: number, end?: number, contentType?: string) => Blob;
223
+ stream: () => ReadableStream<Uint8Array<ArrayBuffer>>;
224
+ text: () => Promise<string>;
225
+ };
226
+ url: string;
227
+ coords: {
228
+ x: number;
229
+ y: number;
230
+ width: number;
231
+ height: number;
232
+ rotation: number;
233
+ flipX: boolean;
234
+ flipY: boolean;
235
+ scale: number;
236
+ };
237
+ width: number;
238
+ height: number;
239
+ originalWidth: number;
240
+ originalHeight: number;
241
+ } | null>;
242
+ }, {}, {}, {}, import("vue").ComponentOptionsMixin, import("vue").ComponentOptionsMixin, {
243
+ done: (result: CropResult) => any;
244
+ ready: (dimensions: {
245
+ width: number;
246
+ height: number;
247
+ }) => any;
248
+ change: (crop: {
249
+ x: number;
250
+ y: number;
251
+ width: number;
252
+ height: number;
253
+ }) => any;
254
+ cancel: () => any;
255
+ remove: () => any;
256
+ uploaded: (result: unknown) => any;
257
+ error: (error: CropVueError) => any;
258
+ "queue-change": (items: QueueItem[]) => any;
259
+ "update:modelValue": (result: CropResult | null) => any;
260
+ }, string, import("vue").PublicProps, Readonly<__VLS_Props> & Readonly<{
261
+ onDone?: ((result: CropResult) => any) | undefined;
262
+ onReady?: ((dimensions: {
263
+ width: number;
264
+ height: number;
265
+ }) => any) | undefined;
266
+ onChange?: ((crop: {
267
+ x: number;
268
+ y: number;
269
+ width: number;
270
+ height: number;
271
+ }) => any) | undefined;
272
+ onCancel?: (() => any) | undefined;
273
+ onRemove?: (() => any) | undefined;
274
+ onUploaded?: ((result: unknown) => any) | undefined;
275
+ onError?: ((error: CropVueError) => any) | undefined;
276
+ "onQueue-change"?: ((items: QueueItem[]) => any) | undefined;
277
+ "onUpdate:modelValue"?: ((result: CropResult | null) => any) | undefined;
278
+ }>, {
279
+ pannable: boolean;
280
+ stencil: StencilType;
281
+ src: string | null;
282
+ maxWidth: number;
283
+ maxHeight: number;
284
+ aspectRatio: number | null;
285
+ minWidth: number;
286
+ minHeight: number;
287
+ outputFormat: OutputFormat;
288
+ outputQuality: number;
289
+ outputMaxWidth: number;
290
+ outputMaxHeight: number;
291
+ accept: string[];
292
+ maxFileSize: number;
293
+ multiple: boolean;
294
+ upload: UploadFn | null;
295
+ modelValue: CropResult | null;
296
+ }, {}, {}, {}, string, import("vue").ComponentProvideOptions, false, {}, any>;
297
+ declare const _default: __VLS_WithSlots<typeof __VLS_component, __VLS_Slots>;
298
+ export default _default;
299
+ type __VLS_WithSlots<T, S> = T & {
300
+ new (): {
301
+ $slots: S;
302
+ };
303
+ };
304
+ //# sourceMappingURL=CropVue.vue.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CropVue.vue.d.ts","sourceRoot":"","sources":["../../src/components/CropVue.vue"],"names":[],"mappings":"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"}
@@ -0,0 +1 @@
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const e=require("vue"),_=require("@cropvue/core"),Z=["src"],j={key:0,class:"cropvue-editor__handle cropvue-editor__handle--ne","data-handle":"ne"},K=14,Y=e.defineComponent({__name:"CropEditor",props:{image:{},transform:{},crop:{},pannable:{type:Boolean,default:!0}},emits:["update:transform","update:crop"],setup(f,{expose:x,emit:p}){const t=f,n=p,a=e.ref(),o=e.ref(),i=e.ref(0),c=e.ref(0),m=e.ref(!1),s=e.computed(()=>{const r=t.image;if(!r||i.value===0||c.value===0||r.naturalWidth===0||r.naturalHeight===0)return 1;const l=i.value/r.naturalWidth,v=c.value/r.naturalHeight;return Math.min(l,v,1)}),u=e.computed(()=>{const r=t.image;return r?r.naturalWidth*s.value:0}),D=e.computed(()=>{const r=t.image;return r?r.naturalHeight*s.value:0}),B=e.computed(()=>({x:(i.value-u.value)/2,y:(c.value-D.value)/2})),R=e.computed(()=>{const r=t.transform,l=s.value,v=[];return v.push(`translate(${r.x*l}px, ${r.y*l}px)`),v.push(`scale(${r.flipX?-r.scale:r.scale}, ${r.flipY?-r.scale:r.scale})`),v.push(`rotate(${r.rotation}deg)`),{width:`${u.value}px`,height:`${D.value}px`,transform:v.join(" "),transformOrigin:"center center"}}),M=e.computed(()=>{const r=s.value,l=B.value;return{left:`${t.crop.x*r+l.x}px`,top:`${t.crop.y*r+l.y}px`,width:`${t.crop.width*r}px`,height:`${t.crop.height*r}px`}}),H=e.computed(()=>{const r=t.crop,l=s.value,v=B.value,h=r.x*l+v.x,g=r.y*l+v.y,$=r.width*l,b=r.height*l,V=i.value,N=c.value;let z;if(r.stencil==="circle"){const E=Math.min($,b)/2,k=h+$/2,C=g+b/2;z=`M${k-E},${C} A${E},${E} 0 1,1 ${k+E},${C} A${E},${E} 0 1,1 ${k-E},${C} Z`}else if(r.stencil==="freeform"&&r.points&&r.points.length>=3){const k=r.points.map(C=>`${C.x*l+v.x},${C.y*l+v.y}`);z=`M${k[0]} ${k.slice(1).map(C=>`L${C}`).join(" ")} Z`}else z=`M${h},${g} L${h+$},${g} L${h+$},${g+b} L${h},${g+b} Z`;return{clipPath:`path(evenodd, "${`M0,0 L${V},0 L${V},${N} L0,${N} Z`} ${z}")`}}),I=e.computed(()=>{const r=t.crop,l=s.value,v=B.value,h=r.x*l+v.x,g=r.y*l+v.y,$=r.width*l,b=r.height*l;if(r.stencil==="circle"){const L=Math.min($,b)/2,E=h+$/2,k=g+b/2;return`circle(${L}px at ${E}px ${k}px)`}const V=g,N=i.value-(h+$),z=c.value-(g+b);return`inset(${V}px ${N}px ${z}px ${h}px)`});function d(){o.value&&(i.value=o.value.clientWidth,c.value=o.value.clientHeight)}let y=null;function w(){y&&(y.destroy(),y=null);const r=a.value;r&&(y=_.usePointerHandler(r,{onPan(l,v){t.pannable&&(m.value=!0,n("update:transform",_.handlePan(t.transform,l,v)))},onZoom(l,v,h){t.pannable&&n("update:transform",_.handleZoom(t.transform,l,v,h))},onCropResize(l,v,h){const g=t.image,$=g?{width:g.naturalWidth,height:g.naturalHeight}:{width:t.crop.width,height:t.crop.height};n("update:crop",_.handleCropResize(t.crop,l,v,h,$))},onCropMove(l,v){const h=t.image,g=h?{width:h.naturalWidth,height:h.naturalHeight}:{width:t.crop.width,height:t.crop.height};n("update:crop",_.handleCropMove(t.crop,l,v,g))},onKeyboard(l,v){t.pannable&&n("update:transform",_.handleKeyboard(t.transform,l,v))},getHandleAtPoint(l){const h=l.target?.getAttribute?.("data-handle");if(h)return h;const g=s.value,$=B.value,b=t.crop,V=b.x*g+$.x,N=b.y*g+$.y,z=V+b.width*g,F=N+b.height*g,L=a.value;if(!L)return null;const E=L.getBoundingClientRect(),k=l.clientX-E.left,C=l.clientY-E.top,S=K;if(b.stencil==="circle"){const X=b.width*g/2,T=V+X,A=N+X,Q=T+X*Math.SQRT1_2,U=A-X*Math.SQRT1_2;return Math.abs(k-Q)<S&&Math.abs(C-U)<S?"ne":null}return Math.abs(k-V)<S&&Math.abs(C-N)<S?"nw":Math.abs(k-z)<S&&Math.abs(C-N)<S?"ne":Math.abs(k-V)<S&&Math.abs(C-F)<S?"sw":Math.abs(k-z)<S&&Math.abs(C-F)<S?"se":null},isInsideCropArea(l){const v=s.value,h=B.value,g=t.crop,$=a.value;if(!$)return!1;const b=$.getBoundingClientRect(),V=l.clientX-b.left,N=l.clientY-b.top,z=(V-h.x)/v,F=(N-h.y)/v;return _.isPointInsideStencil(z,F,g)},displayScale:()=>s.value}))}let P=null,W=null;e.onMounted(()=>{d(),w(),o.value&&(P=new ResizeObserver(()=>{W||(W=requestAnimationFrame(()=>{d(),W=null}))}),P.observe(o.value))}),e.onUnmounted(()=>{P?.disconnect(),P=null,W&&(cancelAnimationFrame(W),W=null),y&&(y.destroy(),y=null)}),e.watch(()=>t.image,async()=>{await e.nextTick(),d()});function q(){m.value=!1}return x({editorRef:a,displayScale:s}),(r,l)=>(e.openBlock(),e.createElementBlock("div",{ref_key:"containerRef",ref:o,class:"cropvue-editor"},[e.createElementVNode("div",{ref_key:"editorRef",ref:a,class:e.normalizeClass(["cropvue-editor__viewport",{"cropvue-editor__viewport--panning":m.value}]),tabindex:"0",onPointerup:q},[e.renderSlot(r.$slots,"image",{style:e.normalizeStyle(R.value),image:f.image,transform:f.transform},()=>[f.image?(e.openBlock(),e.createElementBlock("img",{key:0,src:f.image.element.src,class:"cropvue-editor__image",style:e.normalizeStyle(R.value),draggable:"false",alt:""},null,12,Z)):e.createCommentVNode("",!0)]),e.renderSlot(r.$slots,"overlay",{crop:f.crop,clipPath:I.value},()=>[e.createElementVNode("div",{class:"cropvue-editor__overlay",style:e.normalizeStyle(H.value)},null,4)]),e.renderSlot(r.$slots,"crop-area",{crop:f.crop,style:e.normalizeStyle(M.value)},()=>[e.createElementVNode("div",{class:e.normalizeClass(["cropvue-editor__crop-area",{"cropvue-editor__crop-area--circle":f.crop.stencil==="circle"}]),style:e.normalizeStyle(M.value)},[f.crop.stencil!=="circle"?e.renderSlot(r.$slots,"grid",{key:0,crop:f.crop},()=>[l[0]||(l[0]=e.createStaticVNode('<div class="cropvue-editor__grid"><div class="cropvue-editor__grid-line cropvue-editor__grid-line--h1"></div><div class="cropvue-editor__grid-line cropvue-editor__grid-line--h2"></div><div class="cropvue-editor__grid-line cropvue-editor__grid-line--v1"></div><div class="cropvue-editor__grid-line cropvue-editor__grid-line--v2"></div></div>',1))]):e.createCommentVNode("",!0),e.renderSlot(r.$slots,"handles",{crop:f.crop},()=>[f.crop.stencil==="circle"?(e.openBlock(),e.createElementBlock("div",j)):(e.openBlock(),e.createElementBlock(e.Fragment,{key:1},[l[1]||(l[1]=e.createElementVNode("div",{class:"cropvue-editor__handle cropvue-editor__handle--nw","data-handle":"nw"},null,-1)),l[2]||(l[2]=e.createElementVNode("div",{class:"cropvue-editor__handle cropvue-editor__handle--ne","data-handle":"ne"},null,-1)),l[3]||(l[3]=e.createElementVNode("div",{class:"cropvue-editor__handle cropvue-editor__handle--sw","data-handle":"sw"},null,-1)),l[4]||(l[4]=e.createElementVNode("div",{class:"cropvue-editor__handle cropvue-editor__handle--se","data-handle":"se"},null,-1))],64))])],6)])],34)],512))}}),G={class:"cropvue-toolbar"},O=e.defineComponent({__name:"CropToolbar",props:{transform:{}},emits:["rotate-left","rotate-right","flip-x","flip-y","zoom-in","zoom-out","reset"],setup(f,{emit:x}){const p=x;function t(){p("rotate-left")}function n(){p("rotate-right")}function a(){p("flip-x")}function o(){p("flip-y")}function i(){p("zoom-in")}function c(){p("zoom-out")}function m(){p("reset")}return(s,u)=>(e.openBlock(),e.createElementBlock("div",G,[e.renderSlot(s.$slots,"default",{rotateLeft:t,rotateRight:n,flipX:a,flipY:o,zoomIn:i,zoomOut:c,reset:m,transform:f.transform},()=>[e.createElementVNode("div",{class:"cropvue-toolbar__default"},[e.createElementVNode("button",{type:"button",class:"cropvue-toolbar__btn",title:"Rotate left",onClick:t},[...u[0]||(u[0]=[e.createElementVNode("svg",{viewBox:"0 0 24 24",width:"20",height:"20",fill:"none",stroke:"currentColor","stroke-width":"2"},[e.createElementVNode("path",{d:"M2.5 2v6h6M2.66 12a9 9 0 1 0 1.18-4.5"})],-1)])]),e.createElementVNode("button",{type:"button",class:"cropvue-toolbar__btn",title:"Rotate right",onClick:n},[...u[1]||(u[1]=[e.createElementVNode("svg",{viewBox:"0 0 24 24",width:"20",height:"20",fill:"none",stroke:"currentColor","stroke-width":"2"},[e.createElementVNode("path",{d:"M21.5 2v6h-6M21.34 12a9 9 0 1 1-1.18-4.5"})],-1)])]),u[7]||(u[7]=e.createElementVNode("span",{class:"cropvue-toolbar__separator"},null,-1)),e.createElementVNode("button",{type:"button",class:"cropvue-toolbar__btn",title:"Flip horizontal",onClick:a},[...u[2]||(u[2]=[e.createElementVNode("svg",{viewBox:"0 0 24 24",width:"20",height:"20",fill:"none",stroke:"currentColor","stroke-width":"2"},[e.createElementVNode("path",{d:"M8 3H5a2 2 0 0 0-2 2v14a2 2 0 0 0 2 2h3M16 3h3a2 2 0 0 1 2 2v14a2 2 0 0 1-2 2h-3M12 20V4"})],-1)])]),e.createElementVNode("button",{type:"button",class:"cropvue-toolbar__btn",title:"Flip vertical",onClick:o},[...u[3]||(u[3]=[e.createElementVNode("svg",{viewBox:"0 0 24 24",width:"20",height:"20",fill:"none",stroke:"currentColor","stroke-width":"2"},[e.createElementVNode("path",{d:"M3 8V5a2 2 0 0 1 2-2h14a2 2 0 0 1 2 2v3M3 16v3a2 2 0 0 0 2 2h14a2 2 0 0 0 2-2v-3M20 12H4"})],-1)])]),u[8]||(u[8]=e.createElementVNode("span",{class:"cropvue-toolbar__separator"},null,-1)),e.createElementVNode("button",{type:"button",class:"cropvue-toolbar__btn",title:"Zoom out",onClick:c},[...u[4]||(u[4]=[e.createElementVNode("svg",{viewBox:"0 0 24 24",width:"20",height:"20",fill:"none",stroke:"currentColor","stroke-width":"2"},[e.createElementVNode("circle",{cx:"11",cy:"11",r:"8"}),e.createElementVNode("line",{x1:"21",y1:"21",x2:"16.65",y2:"16.65"}),e.createElementVNode("line",{x1:"8",y1:"11",x2:"14",y2:"11"})],-1)])]),e.createElementVNode("button",{type:"button",class:"cropvue-toolbar__btn",title:"Zoom in",onClick:i},[...u[5]||(u[5]=[e.createStaticVNode('<svg viewBox="0 0 24 24" width="20" height="20" fill="none" stroke="currentColor" stroke-width="2"><circle cx="11" cy="11" r="8"></circle><line x1="21" y1="21" x2="16.65" y2="16.65"></line><line x1="11" y1="8" x2="11" y2="14"></line><line x1="8" y1="11" x2="14" y2="11"></line></svg>',1)])]),u[9]||(u[9]=e.createElementVNode("span",{class:"cropvue-toolbar__separator"},null,-1)),e.createElementVNode("button",{type:"button",class:"cropvue-toolbar__btn",title:"Reset",onClick:m},[...u[6]||(u[6]=[e.createElementVNode("svg",{viewBox:"0 0 24 24",width:"20",height:"20",fill:"none",stroke:"currentColor","stroke-width":"2"},[e.createElementVNode("polyline",{points:"1 4 1 10 7 10"}),e.createElementVNode("polyline",{points:"23 20 23 14 17 14"}),e.createElementVNode("path",{d:"M20.49 9A9 9 0 0 0 5.64 5.64L1 10M23 14l-4.64 4.36A9 9 0 0 1 3.51 15"})],-1)])])])])]))}}),J={class:"cropvue"},ee={class:"cropvue__actions"},te=["disabled"],oe={class:"cropvue__done"},ne=["src"],re=e.defineComponent({__name:"CropVue",props:{stencil:{default:"rectangle"},aspectRatio:{default:null},minWidth:{default:0},minHeight:{default:0},maxWidth:{default:1/0},maxHeight:{default:1/0},outputFormat:{default:"auto"},outputQuality:{default:.85},outputMaxWidth:{default:void 0},outputMaxHeight:{default:void 0},accept:{default:()=>["image/*"]},maxFileSize:{default:1/0},multiple:{type:Boolean,default:!1},upload:{type:[Function,null],default:null},src:{default:null},modelValue:{default:null},pannable:{type:Boolean,default:!0}},emits:["ready","change","done","cancel","remove","uploaded","error","queue-change","update:modelValue"],setup(f,{expose:x,emit:p}){const t=f,n=p,a=e.ref("dropzone"),o=_.useCropper({stencil:t.stencil,aspectRatio:t.aspectRatio??void 0,minWidth:t.minWidth,minHeight:t.minHeight,maxWidth:t.maxWidth,maxHeight:t.maxHeight,outputFormat:t.outputFormat,outputQuality:t.outputQuality,outputMaxWidth:t.outputMaxWidth,outputMaxHeight:t.outputMaxHeight}),i=_.useDropzone({accept:t.accept,maxSize:t.maxFileSize,multiple:t.multiple,onFiles:D,onError:d=>n("error",d)}),c=i.dropzoneRef,m=e.ref(null),s=e.ref(!1),u=e.ref(0);async function D(d){if(d.length!==0)try{await o.loadFile(d[0]),a.value="editor",o.image.value&&n("ready",{width:o.image.value.naturalWidth,height:o.image.value.naturalHeight})}catch{n("error",{type:"load-failed",message:"Failed to load image"})}}e.watch(()=>t.src,async d=>{if(d)try{await o.loadUrl(d),a.value="editor",o.image.value&&n("ready",{width:o.image.value.naturalWidth,height:o.image.value.naturalHeight})}catch{n("error",{type:"load-failed",message:"Failed to load image from URL"})}},{immediate:!0}),e.watch(()=>t.stencil,d=>o.setStencil(d)),e.watch(()=>t.aspectRatio,d=>o.setAspectRatio(d??null));async function B(){try{const d=await o.getResult({format:t.outputFormat,quality:t.outputQuality,maxWidth:t.outputMaxWidth,maxHeight:t.outputMaxHeight});if(m.value=d,n("done",d),n("update:modelValue",d),t.upload){s.value=!0,u.value=0;const y=new AbortController;try{const w=await t.upload(d.file,{onProgress:P=>{u.value=P},signal:y.signal});n("uploaded",w)}catch(w){n("error",{type:"upload-failed",message:String(w)})}finally{s.value=!1}}a.value="done"}catch(d){n("error",{type:"compress-failed",message:String(d)})}}function R(){n("cancel"),m.value?a.value="done":(a.value="dropzone",o.reset())}function M(){a.value="dropzone",m.value=null,o.reset()}function H(){n("remove"),n("update:modelValue",null),a.value="dropzone",m.value=null,o.reset()}function I(){a.value="editor"}return x({cropper:o,phase:a,confirm:B,cancel:R,restart:M,reedit:I,remove:H,result:m}),(d,y)=>(e.openBlock(),e.createElementBlock("div",J,[a.value==="dropzone"?(e.openBlock(),e.createElementBlock("div",{key:0,ref_key:"dropzoneRef",ref:c},[e.renderSlot(d.$slots,"dropzone",{open:e.unref(i).open,isDragging:e.unref(i).isDragging.value},()=>[e.createElementVNode("div",{class:e.normalizeClass(["cropvue__dropzone",{"cropvue__dropzone--active":e.unref(i).isDragging.value}]),onClick:y[0]||(y[0]=(...w)=>e.unref(i).open&&e.unref(i).open(...w))},[e.renderSlot(d.$slots,"dropzone-content",{open:e.unref(i).open,isDragging:e.unref(i).isDragging.value},()=>[y[5]||(y[5]=e.createElementVNode("p",null,"Drop image here or click to select",-1))])],2)])],512)):e.createCommentVNode("",!0),a.value==="editor"?(e.openBlock(),e.createElementBlock(e.Fragment,{key:1},[e.renderSlot(d.$slots,"editor",{image:e.unref(o).image.value,transform:e.unref(o).transform.value,crop:e.unref(o).crop.value,rotateLeft:e.unref(o).rotateLeft,rotateRight:e.unref(o).rotateRight,flipX:e.unref(o).flipX,flipY:e.unref(o).flipY,zoomIn:()=>e.unref(o).zoomBy(.1),zoomOut:()=>e.unref(o).zoomBy(-.1),reset:e.unref(o).reset,confirm:B,cancel:R,remove:H,pannable:f.pannable},()=>[e.createVNode(Y,{image:e.unref(o).image.value,transform:e.unref(o).transform.value,crop:e.unref(o).crop.value,pannable:f.pannable,"onUpdate:transform":y[1]||(y[1]=w=>e.unref(o).transform.value=w),"onUpdate:crop":y[2]||(y[2]=w=>e.unref(o).crop.value=w)},null,8,["image","transform","crop","pannable"])]),e.renderSlot(d.$slots,"toolbar",{rotateLeft:e.unref(o).rotateLeft,rotateRight:e.unref(o).rotateRight,flipX:e.unref(o).flipX,flipY:e.unref(o).flipY,zoomIn:()=>e.unref(o).zoomBy(.1),zoomOut:()=>e.unref(o).zoomBy(-.1),reset:e.unref(o).reset,transform:e.unref(o).transform.value},()=>[e.createVNode(O,{transform:e.unref(o).transform.value,onRotateLeft:e.unref(o).rotateLeft,onRotateRight:e.unref(o).rotateRight,onFlipX:e.unref(o).flipX,onFlipY:e.unref(o).flipY,onZoomIn:y[3]||(y[3]=()=>e.unref(o).zoomBy(.1)),onZoomOut:y[4]||(y[4]=()=>e.unref(o).zoomBy(-.1)),onReset:e.unref(o).reset},null,8,["transform","onRotateLeft","onRotateRight","onFlipX","onFlipY","onReset"])]),e.renderSlot(d.$slots,"preview",{image:e.unref(o).image.value,transform:e.unref(o).transform.value,crop:e.unref(o).crop.value}),e.renderSlot(d.$slots,"actions",{confirm:B,cancel:R,remove:H,isUploading:s.value,progress:u.value},()=>[e.createElementVNode("div",ee,[e.createElementVNode("button",{type:"button",class:"cropvue__btn cropvue__btn--cancel",onClick:R},"Cancel"),e.createElementVNode("button",{type:"button",class:"cropvue__btn cropvue__btn--confirm",disabled:s.value,onClick:B},e.toDisplayString(s.value?"Uploading...":"Confirm"),9,te)])])],64)):e.createCommentVNode("",!0),a.value==="done"?e.renderSlot(d.$slots,"done",{key:2,result:m.value,restart:M,reedit:I,remove:H},()=>[e.createElementVNode("div",oe,[m.value?(e.openBlock(),e.createElementBlock("img",{key:0,src:m.value.url,alt:"Cropped result",class:"cropvue__result-image"},null,8,ne)):e.createCommentVNode("",!0),e.createElementVNode("button",{type:"button",class:"cropvue__btn",onClick:M},"Crop another")])]):e.createCommentVNode("",!0),e.renderSlot(d.$slots,"error"),s.value?e.renderSlot(d.$slots,"loading",{key:3,progress:u.value}):e.createCommentVNode("",!0)]))}}),le={class:"cropvue-preview"},ae=e.defineComponent({__name:"CropPreview",props:{image:{},transform:{},crop:{},maxWidth:{default:void 0},maxHeight:{default:void 0},debounce:{default:50}},setup(f,{expose:x}){const p=f,t=e.ref(null);let n;function a(){const i=t.value,c=p.image;!i||!c||_.renderCrop(i,c.element,p.crop,p.transform,{maxWidth:p.maxWidth,maxHeight:p.maxHeight})}function o(){n&&clearTimeout(n),n=setTimeout(a,p.debounce)}return e.watch([()=>p.transform,()=>p.crop,()=>p.image],o,{deep:!0}),e.onMounted(()=>{p.image&&a()}),e.onUnmounted(()=>{n&&clearTimeout(n)}),x({canvasRef:t,render:a}),(i,c)=>(e.openBlock(),e.createElementBlock("div",le,[e.renderSlot(i.$slots,"default",{canvasRef:t.value,render:a},()=>[e.createElementVNode("canvas",{ref_key:"canvasRef",ref:t,class:"cropvue-preview__canvas"},null,512)])]))}}),ie=e.defineComponent({__name:"CropDropzone",props:{accept:{default:()=>["image/*"]},maxSize:{default:1/0},multiple:{type:Boolean,default:!1}},emits:["files","error"],setup(f,{expose:x,emit:p}){const t=f,n=p,{isDragging:a,files:o,dropzoneRef:i,open:c}=_.useDropzone({accept:t.accept,maxSize:t.maxSize,multiple:t.multiple,onFiles:m=>n("files",m),onError:m=>n("error",m)});return x({open:c,files:o}),(m,s)=>(e.openBlock(),e.createElementBlock("div",{ref_key:"dropzoneRef",ref:i,class:e.normalizeClass(["cropvue-dropzone",{"cropvue-dropzone--active":e.unref(a)}])},[e.renderSlot(m.$slots,"default",{open:e.unref(c),isDragging:e.unref(a)},()=>[e.createElementVNode("div",{class:"cropvue-dropzone__default",onClick:s[0]||(s[0]=(...u)=>e.unref(c)&&e.unref(c)(...u))},[...s[1]||(s[1]=[e.createElementVNode("p",null,"Drop image here or click to select",-1)])])])],2))}}),se={class:"cropvue-queue"},ue={class:"cropvue-queue__list"},ce=["onClick"],de=["src","alt"],pe=["onClick"],me={key:0,class:"cropvue-queue__check"},fe=e.defineComponent({__name:"CropQueue",emits:["select","remove","change"],setup(f,{expose:x,emit:p}){const t=p,n=_.useImageQueue();function a(i){const c=n.images.value[i];c&&(n.select(i),t("select",c))}function o(i){const c=n.images.value[i];c&&(n.remove(i),t("remove",c),t("change",n.images.value))}return x({queue:n}),(i,c)=>(e.openBlock(),e.createElementBlock("div",se,[e.renderSlot(i.$slots,"default",{items:e.unref(n).images.value,currentIndex:e.unref(n).current.value,select:a,remove:o,add:e.unref(n).add},()=>[e.createElementVNode("div",ue,[(e.openBlock(!0),e.createElementBlock(e.Fragment,null,e.renderList(e.unref(n).images.value,(m,s)=>(e.openBlock(),e.createElementBlock("div",{key:m.id,class:e.normalizeClass(["cropvue-queue__item",{"cropvue-queue__item--active":e.unref(n).current.value===s,"cropvue-queue__item--done":m.status==="done"}]),onClick:u=>a(s)},[e.createElementVNode("img",{src:m.thumbnail,alt:`Queue item ${s+1}`,class:"cropvue-queue__thumbnail"},null,8,de),e.createElementVNode("button",{type:"button",class:"cropvue-queue__remove",title:"Remove",onClick:e.withModifiers(u=>o(s),["stop"])},[...c[0]||(c[0]=[e.createElementVNode("svg",{viewBox:"0 0 24 24",width:"14",height:"14",fill:"none",stroke:"currentColor","stroke-width":"2"},[e.createElementVNode("line",{x1:"18",y1:"6",x2:"6",y2:"18"}),e.createElementVNode("line",{x1:"6",y1:"6",x2:"18",y2:"18"})],-1)])],8,pe),m.status==="done"?(e.openBlock(),e.createElementBlock("div",me,[...c[1]||(c[1]=[e.createElementVNode("svg",{viewBox:"0 0 24 24",width:"16",height:"16",fill:"none",stroke:"currentColor","stroke-width":"3"},[e.createElementVNode("polyline",{points:"20 6 9 17 4 12"})],-1)])])):e.createCommentVNode("",!0)],10,ce))),128))])])]))}}),ve={class:"cropvue-stencil"},he=e.defineComponent({__name:"CropStencil",props:{crop:{},containerWidth:{},containerHeight:{}},setup(f){const x=f,p=e.computed(()=>{const n=x.crop;if(n.stencil==="circle"){const m=Math.min(n.width,n.height)/2,s=n.x+n.width/2,u=n.y+n.height/2;return`circle(${m}px at ${s}px ${u}px)`}if(n.stencil==="freeform"&&n.points&&n.points.length>=3)return`polygon(${n.points.map(s=>`${s.x}px ${s.y}px`).join(", ")})`;const a=n.y,o=x.containerWidth-(n.x+n.width),i=x.containerHeight-(n.y+n.height),c=n.x;return`inset(${a}px ${o}px ${i}px ${c}px)`}),t=e.computed(()=>({clipPath:p.value,WebkitClipPath:p.value}));return(n,a)=>(e.openBlock(),e.createElementBlock("div",ve,[e.renderSlot(n.$slots,"default",{clipPath:p.value,style:e.normalizeStyle(t.value),crop:f.crop,stencil:f.crop.stencil,points:f.crop.points},()=>[e.createElementVNode("div",{class:"cropvue-stencil__shape",style:e.normalizeStyle(t.value)},null,4)])]))}});Object.defineProperty(exports,"useCompressor",{enumerable:!0,get:()=>_.useCompressor});Object.defineProperty(exports,"useCropper",{enumerable:!0,get:()=>_.useCropper});Object.defineProperty(exports,"useDropzone",{enumerable:!0,get:()=>_.useDropzone});Object.defineProperty(exports,"useImageQueue",{enumerable:!0,get:()=>_.useImageQueue});Object.defineProperty(exports,"useUploader",{enumerable:!0,get:()=>_.useUploader});exports.CropDropzone=ie;exports.CropEditor=Y;exports.CropPreview=ae;exports.CropQueue=fe;exports.CropStencil=he;exports.CropToolbar=O;exports.CropVue=re;