@@ -16,15 +16,26 @@ tmpl.innerHTML = `
1616
1717function moveCropArea ( event ) {
1818 const el = event . currentTarget
19- if ( el . dragStartX && el . dragStartY ) {
20- const x = Math . min (
21- Math . max ( 0 , el . box . offsetLeft + event . pageX - el . dragStartX ) ,
22- el . image . width - el . box . offsetWidth
23- )
24- const y = Math . min (
25- Math . max ( 0 , el . box . offsetTop + event . pageY - el . dragStartY ) ,
26- el . image . height - el . box . offsetHeight
27- )
19+ let deltaX = 0
20+ let deltaY = 0
21+ if ( event . type === 'keydown' ) {
22+ if ( event . key === 'ArrowUp' ) {
23+ deltaY = - 1
24+ } else if ( event . key === 'ArrowDown' ) {
25+ deltaY = 1
26+ } else if ( event . key === 'ArrowLeft' ) {
27+ deltaX = - 1
28+ } else if ( event . key === 'ArrowRight' ) {
29+ deltaX = 1
30+ }
31+ } else if ( el . dragStartX && el . dragStartY ) {
32+ deltaX = event . pageX - el . dragStartX
33+ deltaY = event . pageY - el . dragStartY
34+ }
35+
36+ if ( deltaX !== 0 || deltaY !== 0 ) {
37+ const x = Math . min ( Math . max ( 0 , el . box . offsetLeft + deltaX ) , el . image . width - el . box . offsetWidth )
38+ const y = Math . min ( Math . max ( 0 , el . box . offsetTop + deltaY ) , el . image . height - el . box . offsetHeight )
2839 el . box . style . left = `${ x } px`
2940 el . box . style . top = `${ y } px`
3041
@@ -38,9 +49,22 @@ function moveCropArea(event) {
3849function updateCropArea ( event ) {
3950 const el = event . target . closest ( 'image-crop' )
4051 const rect = el . getBoundingClientRect ( )
41- const deltaX = event . pageX - el . startX - rect . left - window . pageXOffset
42- const deltaY = event . pageY - el . startY - rect . top - window . pageYOffset
43- updateDimensions ( el , deltaX , deltaY )
52+ let deltaX , deltaY , delta
53+ if ( event . key ) {
54+ if ( event . key === 'Escape' ) return setInitialPosition ( el )
55+ if ( event . key === '-' ) delta = - 10
56+ if ( event . key === '=' ) delta = + 10
57+ if ( ! delta ) return
58+ deltaX = el . box . offsetWidth + delta
59+ deltaY = el . box . offsetHeight + delta
60+ el . startX = el . box . offsetLeft
61+ el . startY = el . box . offsetTop
62+ } else {
63+ deltaX = event . pageX - el . startX - rect . left - window . pageXOffset
64+ deltaY = event . pageY - el . startY - rect . top - window . pageYOffset
65+ }
66+
67+ if ( deltaX && deltaY ) updateDimensions ( el , deltaX , deltaY , ! event . key )
4468}
4569
4670function startUpdate ( event ) {
@@ -60,19 +84,24 @@ function startUpdate(event) {
6084 }
6185}
6286
63- function updateDimensions ( target , deltaX , deltaY ) {
87+ function updateDimensions ( target , deltaX , deltaY , reposition = true ) {
6488 let newSide = Math . max ( Math . abs ( deltaX ) , Math . abs ( deltaY ) , target . minWidth )
6589 newSide = Math . min (
6690 newSide ,
6791 deltaY > 0 ? target . image . height - target . startY : target . startY ,
6892 deltaX > 0 ? target . image . width - target . startX : target . startX
6993 )
7094
71- const x = Math . round ( Math . max ( 0 , deltaX > 0 ? target . startX : target . startX - newSide ) )
72- const y = Math . round ( Math . max ( 0 , deltaY > 0 ? target . startY : target . startY - newSide ) )
95+ const x = reposition
96+ ? Math . round ( Math . max ( 0 , deltaX > 0 ? target . startX : target . startX - newSide ) )
97+ : target . box . offsetLeft
98+ const y = reposition
99+ ? Math . round ( Math . max ( 0 , deltaY > 0 ? target . startY : target . startY - newSide ) )
100+ : target . box . offsetTop
73101
74102 target . box . style . left = `${ x } px`
75103 target . box . style . top = `${ y } px`
104+
76105 target . box . style . width = `${ newSide } px`
77106 target . box . style . height = `${ newSide } px`
78107 fireChangeEvent ( target , { x, y, width : newSide , height : newSide } )
@@ -81,7 +110,11 @@ function updateDimensions(target, deltaX, deltaY) {
81110function imageReady ( event ) {
82111 const el = event . currentTarget . closest ( 'image-crop' )
83112 el . loaded = true
84- const image = event . target
113+ setInitialPosition ( el )
114+ }
115+
116+ function setInitialPosition ( el ) {
117+ const image = el . image
85118 const side = Math . round ( image . clientWidth > image . clientHeight ? image . clientHeight : image . clientWidth )
86119 el . startX = ( image . clientWidth - side ) / 2
87120 el . startY = ( image . clientHeight - side ) / 2
@@ -128,6 +161,8 @@ export class ImageCropElement extends HTMLElement {
128161 this . addEventListener ( 'mouseleave' , stopUpdate )
129162 this . addEventListener ( 'mouseup' , stopUpdate )
130163 this . box . addEventListener ( 'mousedown' , startUpdate )
164+ this . addEventListener ( 'keydown' , moveCropArea )
165+ this . addEventListener ( 'keydown' , updateCropArea )
131166
132167 if ( this . src ) this . image . src = this . src
133168 }
0 commit comments