@atlaskit/editor-plugin-media-editing
Version:
MediaEditing plugin for @atlaskit/editor-core
530 lines (503 loc) • 24.1 kB
JavaScript
/* Cropper.tsx generated by @compiled/babel-plugin v0.39.1 */
"use strict";
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
var _typeof = require("@babel/runtime/helpers/typeof");
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.Cropper = void 0;
var _runtime = require("@compiled/react/runtime");
var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
var _slicedToArray2 = _interopRequireDefault(require("@babel/runtime/helpers/slicedToArray"));
var _react = _interopRequireWildcard(require("react"));
var _bindEventListener = require("bind-event-listener");
function _interopRequireWildcard(e, t) { if ("function" == typeof WeakMap) var r = new WeakMap(), n = new WeakMap(); return (_interopRequireWildcard = function _interopRequireWildcard(e, t) { if (!t && e && e.__esModule) return e; var o, i, f = { __proto__: null, default: e }; if (null === e || "object" != _typeof(e) && "function" != typeof e) return f; if (o = t ? n : r) { if (o.has(e)) return o.get(e); o.set(e, f); } for (var _t in e) "default" !== _t && {}.hasOwnProperty.call(e, _t) && ((i = (o = Object.defineProperty) && Object.getOwnPropertyDescriptor(e, _t)) && (i.get || i.set) ? o(f, _t, i) : f[_t] = e[_t]); return f; })(e, t); }
function ownKeys(e, r) { var t = Object.keys(e); if (Object.getOwnPropertySymbols) { var o = Object.getOwnPropertySymbols(e); r && (o = o.filter(function (r) { return Object.getOwnPropertyDescriptor(e, r).enumerable; })), t.push.apply(t, o); } return t; }
function _objectSpread(e) { for (var r = 1; r < arguments.length; r++) { var t = null != arguments[r] ? arguments[r] : {}; r % 2 ? ownKeys(Object(t), !0).forEach(function (r) { (0, _defineProperty2.default)(e, r, t[r]); }) : Object.getOwnPropertyDescriptors ? Object.defineProperties(e, Object.getOwnPropertyDescriptors(t)) : ownKeys(Object(t)).forEach(function (r) { Object.defineProperty(e, r, Object.getOwnPropertyDescriptor(t, r)); }); } return e; }
var isSSRRender = function isSSRRender() {
return typeof document === 'undefined' || process.env.REACT_SSR === 'true';
};
/**
* Props for the Cropper component
*/
// Type-safe intrinsic element types for CropperJS web components (local to this file)
// Helper to create web component elements with proper typing
var CropperCanvas = 'cropper-canvas';
var CropperImage = 'cropper-image';
var CropperSelection = 'cropper-selection';
var CropperShade = 'cropper-shade';
var CropperGrid = 'cropper-grid';
var CropperCrosshair = 'cropper-crosshair';
var CropperHandle = 'cropper-handle';
/**
* Options for getting the cropped canvas
*/
/**
* Methods exposed via ref
*/
/**
* Cropper component - A React wrapper for CropperJS 2.x web components
*
* @example
* ```tsx
* const cropperRef = useRef<CropperRef>(null);
*
* <Cropper
* ref={cropperRef}
* src="/image.jpg"
* aspectRatio={16/9}
* onReady={(canvas) => console.log('Ready!')}
* onChange={(e) => console.log(e.detail.bounds)}
* />
* ```
*/
var Cropper = exports.Cropper = /*#__PURE__*/(0, _react.forwardRef)(function (_ref, ref) {
var src = _ref.src,
_ref$alt = _ref.alt,
alt = _ref$alt === void 0 ? '' : _ref$alt,
crossOrigin = _ref.crossOrigin,
aspectRatio = _ref.aspectRatio,
initialAspectRatio = _ref.initialAspectRatio,
_ref$initialCoverage = _ref.initialCoverage,
initialCoverage = _ref$initialCoverage === void 0 ? 1 : _ref$initialCoverage,
_ref$background = _ref.background,
background = _ref$background === void 0 ? true : _ref$background,
_ref$rotatable = _ref.rotatable,
rotatable = _ref$rotatable === void 0 ? true : _ref$rotatable,
_ref$scalable = _ref.scalable,
scalable = _ref$scalable === void 0 ? true : _ref$scalable,
_ref$translatable = _ref.translatable,
translatable = _ref$translatable === void 0 ? true : _ref$translatable,
_ref$movable = _ref.movable,
movable = _ref$movable === void 0 ? true : _ref$movable,
_ref$resizable = _ref.resizable,
resizable = _ref$resizable === void 0 ? true : _ref$resizable,
_ref$zoomable = _ref.zoomable,
zoomable = _ref$zoomable === void 0 ? true : _ref$zoomable,
_ref$multiple = _ref.multiple,
multiple = _ref$multiple === void 0 ? false : _ref$multiple,
_ref$outlined = _ref.outlined,
outlined = _ref$outlined === void 0 ? true : _ref$outlined,
className = _ref.className,
onImageReady = _ref.onImageReady,
_ref$isCircle = _ref.isCircle,
isCircle = _ref$isCircle === void 0 ? false : _ref$isCircle;
var canvasRef = (0, _react.useRef)(null);
var selectionRef = (0, _react.useRef)(null);
var imageRef = (0, _react.useRef)(null);
var previousSelectionRef = (0, _react.useRef)(null);
var _useState = (0, _react.useState)(false),
_useState2 = (0, _slicedToArray2.default)(_useState, 2),
isImageReady = _useState2[0],
setIsImageReady = _useState2[1];
var _useState3 = (0, _react.useState)(false),
_useState4 = (0, _slicedToArray2.default)(_useState3, 2),
isCropperLoaded = _useState4[0],
setIsCropperLoaded = _useState4[1];
var getCanvas = (0, _react.useCallback)(function () {
return canvasRef.current;
}, []);
var getImage = (0, _react.useCallback)(function () {
return imageRef.current;
}, []);
var getSelection = (0, _react.useCallback)(function () {
return selectionRef.current;
}, []);
var getCroppedCanvas = (0, _react.useCallback)(function (options) {
var selection = selectionRef.current;
if (!selection) {
return Promise.resolve(null);
}
// Check if the $toCanvas method exists (web component might not be fully initialized)
if (typeof selection.$toCanvas !== 'function') {
return Promise.resolve(null);
}
// If circular crop, we need to apply a circular mask
if (isCircle) {
// For circular crops, force square dimensions to maintain perfect circle
var squareOptions = _objectSpread(_objectSpread({}, options), {}, {
height: options === null || options === void 0 ? void 0 : options.width // Make height equal to width for a perfect circle
});
return selection.$toCanvas(_objectSpread(_objectSpread({}, squareOptions), {}, {
beforeDraw: function beforeDraw(context, canvas) {
// For circles, ensure we have a square canvas
var size = Math.min(canvas.width, canvas.height);
var radius = size / 2;
var centerX = size / 2;
var centerY = size / 2;
// Enable high-quality image rendering
context.imageSmoothingEnabled = true;
context.imageSmoothingQuality = 'high';
// Create a circular clipping path with anti-aliasing
context.beginPath();
context.arc(centerX, centerY, radius, 0, Math.PI * 2);
context.clip();
}
}));
}
return selection.$toCanvas(options);
}, [isCircle]);
var fitStencilToImage = (0, _react.useCallback)(function () {
var canvas = canvasRef.current;
var image = imageRef.current;
var selection = selectionRef.current;
if (canvas && image && selection) {
// Get the real time positions
var canvasRect = canvas.getBoundingClientRect();
var imageRect = image.getBoundingClientRect();
// Calculate coordinates relative to the canvas
requestAnimationFrame(function () {
var x = imageRect.left - canvasRect.left;
var y = imageRect.top - canvasRect.top;
var width = imageRect.width;
var height = imageRect.height;
// Apply these to the selection (the stencil)
if (typeof selection.$change === 'function') {
selection.$change(Math.floor(x), Math.floor(y), Math.floor(width), Math.floor(height));
}
});
}
}, []);
// Clamp position to keep crop area within image boundaries
var clampPosition = (0, _react.useCallback)(function (current) {
var canvas = canvasRef.current;
var image = imageRef.current;
if (!canvas || !image) {
return null;
}
var canvasRect = canvas.getBoundingClientRect();
var imageRect = image.getBoundingClientRect();
var imageX = imageRect.left - canvasRect.left;
var imageY = imageRect.top - canvasRect.top;
var imageWidth = imageRect.width;
var imageHeight = imageRect.height;
var clampedX = current.x;
var clampedY = current.y;
// Clamp left/right
if (clampedX < imageX) {
clampedX = imageX;
} else if (clampedX + current.width > imageX + imageWidth) {
clampedX = imageX + imageWidth - current.width;
}
// Clamp top/bottom
if (clampedY < imageY) {
clampedY = imageY;
} else if (clampedY + current.height > imageY + imageHeight) {
clampedY = imageY + imageHeight - current.height;
}
return {
x: clampedX,
y: clampedY
};
}, []);
// Correct dimensions when resizing with aspect ratio constraints
var correctResizeDimensions = (0, _react.useCallback)(function (current, selection) {
var canvas = canvasRef.current;
var image = imageRef.current;
if (!canvas || !image) {
return null;
}
var canvasRect = canvas.getBoundingClientRect();
var imageRect = image.getBoundingClientRect();
var imageX = imageRect.left - canvasRect.left;
var imageY = imageRect.top - canvasRect.top;
var imageWidth = imageRect.width;
var imageHeight = imageRect.height;
var maxWidthAvailable = imageX + imageWidth - current.x;
var maxHeightAvailable = imageY + imageHeight - current.y;
var correctedWidth = current.width;
var correctedHeight = current.height;
var hasAspectRatio = selection.aspectRatio && selection.aspectRatio > 0;
if (hasAspectRatio) {
var _aspectRatio = selection.aspectRatio;
var heightIfMaxWidth = maxWidthAvailable / _aspectRatio;
var widthIfMaxHeight = maxHeightAvailable * _aspectRatio;
// Determine which axis is the limiting factor
if (heightIfMaxWidth <= maxHeightAvailable) {
correctedWidth = maxWidthAvailable;
correctedHeight = heightIfMaxWidth;
} else {
correctedHeight = maxHeightAvailable;
correctedWidth = widthIfMaxHeight;
}
} else {
correctedWidth = Math.min(correctedWidth, maxWidthAvailable);
correctedHeight = Math.min(correctedHeight, maxHeightAvailable);
}
// Ensure positive dimensions
correctedWidth = Math.max(1, correctedWidth);
correctedHeight = Math.max(1, correctedHeight);
return {
width: correctedWidth,
height: correctedHeight
};
}, []);
// Handle move operation (position changed but size stayed same)
var handleMove = (0, _react.useCallback)(function () {
requestAnimationFrame(function () {
var selection = selectionRef.current;
if (!selection) {
return;
}
var current = {
x: selection.x || 0,
y: selection.y || 0,
width: selection.width || 0,
height: selection.height || 0
};
var clamped = clampPosition(current);
if (!clamped) {
return;
}
if (typeof selection.$change === 'function') {
selection.$change(Math.floor(clamped.x), Math.floor(clamped.y), Math.floor(current.width), Math.floor(current.height));
}
previousSelectionRef.current = {
width: current.width,
height: current.height
};
});
}, [clampPosition]);
// Handle resize operation (size changed, may need aspect ratio correction)
var handleResize = (0, _react.useCallback)(function () {
requestAnimationFrame(function () {
var selection = selectionRef.current;
if (!selection) {
return;
}
var current = {
x: selection.x || 0,
y: selection.y || 0,
width: selection.width || 0,
height: selection.height || 0
};
var corrected = correctResizeDimensions(current, selection);
if (!corrected) {
return;
}
var canvas = canvasRef.current;
var image = imageRef.current;
if (!canvas || !image) {
return;
}
var canvasRect = canvas.getBoundingClientRect();
var imageRect = image.getBoundingClientRect();
var imageX = imageRect.left - canvasRect.left;
var imageY = imageRect.top - canvasRect.top;
var correctedX = Math.max(imageX, current.x);
var correctedY = Math.max(imageY, current.y);
if (typeof selection.$change === 'function') {
selection.$change(Math.floor(correctedX), Math.floor(correctedY), Math.floor(corrected.width), Math.floor(corrected.height));
}
previousSelectionRef.current = {
width: corrected.width,
height: corrected.height
};
});
}, [correctResizeDimensions]);
// Check if selection is within image boundaries
var isSelectionOutOfBounds = (0, _react.useCallback)(function (imageX, imageY, imageWidth, imageHeight, selection) {
var tolerance = 1;
return selection.x < imageX - tolerance || selection.y < imageY - tolerance || selection.x + selection.width > imageX + imageWidth + tolerance || selection.y + selection.height > imageY + imageHeight + tolerance;
}, []);
// Detect if operation is a move or resize based on dimension change
var isMovingSelection = (0, _react.useCallback)(function () {
var prev = previousSelectionRef.current;
var curr = selectionRef.current;
if (!prev || !curr) {
return false;
}
return prev.width === curr.width && prev.height === curr.height;
}, []);
var handleSelectionChange = (0, _react.useCallback)(function (event) {
var canvas = canvasRef.current;
var image = imageRef.current;
var customEvent = event;
var selection = customEvent.detail;
if (!canvas || !image || !selection) {
return;
}
var canvasRect = canvas.getBoundingClientRect();
var imageRect = image.getBoundingClientRect();
var imageX = imageRect.left - canvasRect.left;
var imageY = imageRect.top - canvasRect.top;
var imageWidth = imageRect.width;
var imageHeight = imageRect.height;
if (!isSelectionOutOfBounds(imageX, imageY, imageWidth, imageHeight, selection)) {
previousSelectionRef.current = {
width: selection.width,
height: selection.height
};
return;
}
if (isMovingSelection()) {
handleMove();
} else {
handleResize();
}
}, [isSelectionOutOfBounds, isMovingSelection, handleMove, handleResize]);
// Lazy load cropperjs only on the client to avoid SSR side effects
(0, _react.useEffect)(function () {
if (!isSSRRender()) {
Promise.resolve().then(function () {
return _interopRequireWildcard(require('cropperjs'));
}).then(function () {
return setIsCropperLoaded(true);
}).catch(function () {
setIsCropperLoaded(false);
});
}
}, []);
// Auto-fit stencil to image on mount and when src changes
// Only run after cropperjs has loaded (client-side only, post-hydration)
(0, _react.useEffect)(function () {
if (!isCropperLoaded) {
return;
}
// eslint-disable-next-line @atlassian/perf-linting/no-chain-state-updates -- Ignored via go/ees017 (to be fixed)
setIsImageReady(false); // Hide canvas while repositioning
var image = imageRef.current;
if (!image) {
return;
}
// Wait for the image to be fully loaded
if (typeof image.$ready === 'function') {
image.$ready(function () {
var timer = setTimeout(function () {
fitStencilToImage();
setIsImageReady(true);
onImageReady === null || onImageReady === void 0 || onImageReady(true);
}, 500); // Adding a small timeout as there is a rendering issue with webkit
return function () {
return clearTimeout(timer);
};
});
} else {
// Fallback to timeout if $ready is not available
var timer = setTimeout(function () {
fitStencilToImage();
setIsImageReady(true);
onImageReady === null || onImageReady === void 0 || onImageReady(true);
}, 2000);
return function () {
return clearTimeout(timer);
};
}
}, [src, isCropperLoaded, onImageReady, fitStencilToImage]);
// Attach selection change listener to enforce boundaries (only after image is ready)
(0, _react.useEffect)(function () {
if (!isImageReady) {
return;
}
var selection = selectionRef.current;
if (!selection) {
return;
}
return (0, _bindEventListener.bind)(selection, {
type: 'change',
listener: handleSelectionChange
});
}, [isImageReady, handleSelectionChange]);
(0, _react.useEffect)(function () {
if (!canvasRef.current || !imageRef.current) {
return;
}
var observer = new ResizeObserver(function () {
var _imageRef$current;
// This forces the image to recalculate its "contain" logic
// whenever the canvas wrapper changes size
if (typeof ((_imageRef$current = imageRef.current) === null || _imageRef$current === void 0 ? void 0 : _imageRef$current.$center) === 'function') {
var _imageRef$current2;
(_imageRef$current2 = imageRef.current) === null || _imageRef$current2 === void 0 || _imageRef$current2.$center('contain');
}
});
observer.observe(canvasRef.current);
return function () {
return observer.disconnect();
};
}, [canvasRef, imageRef]);
(0, _react.useEffect)(function () {
if (!canvasRef.current) {
return;
}
var observer = new ResizeObserver(function () {
var _selectionRef$current;
(_selectionRef$current = selectionRef.current) === null || _selectionRef$current === void 0 || _selectionRef$current.removeAttribute('aspect-ratio');
fitStencilToImage();
});
observer.observe(canvasRef.current);
return function () {
return observer.disconnect();
};
}, [fitStencilToImage]);
(0, _react.useImperativeHandle)(ref, function () {
return {
fitStencilToImage: fitStencilToImage,
getCanvas: getCanvas,
getCroppedCanvas: getCroppedCanvas,
getImage: getImage,
isImageReady: isImageReady,
getSelection: getSelection
};
}, [getCanvas, getCroppedCanvas, getImage, isImageReady, fitStencilToImage, getSelection]);
// Inject global styles for cropper handles
(0, _react.useEffect)(function () {
var style = document.createElement('style');
var circularStyle = isCircle ? "\n\t\t\tcropper-selection {\n\t\t\t\toutline: none;\n\t\t\t\tborder-top: 1px solid #0052CC;\n\t\t\t\tborder-right: 1px solid #0052CC;\n\t\t\t\tborder-bottom: 1px solid #0052CC;\n\t\t\t\tborder-left: 1px solid #0052CC;\n\t\t\t\tbox-sizing: border-box;\n\t\t\t\tborder-radius: 50%;\n\t\t\t\tbox-shadow: 0 0 0 9999px rgba(255, 255, 255, 0.6);\n\t\t\t}\n\t\t" : "\n\t\t\tcropper-selection {\n\t\t\t\toutline: none;\n\t\t\t\tborder-top: 1px solid #0052CC;\n\t\t\t\tborder-right: 1px solid #0052CC;\n\t\t\t\tborder-bottom: 1px solid #0052CC;\n\t\t\t\tborder-left: 1px solid #0052CC;\n\t\t\t\tbox-sizing: border-box; \n\t\t\t}\n\t\t";
style.textContent = "\n\t\t\t\tcropper-canvas {\n\t\t\t\t\tbackground-color: #F8F8F8;\n\t\t\t\t\tbackground-image: none;\n\t\t\t\t}\n\t\t\t\tcropper-shade {\n\t\t\t\t\toutline-color: rgba(255,255,255,0.5);\n\t\t\t\t}\n\t\t\t\tcropper-handle[action=\"move\"] {\n\t\t\t\t\topacity: 0;\n\t\t\t\t}\n\t\t\t\tcropper-handle[action=\"ne-resize\"] {\n\t\t\t\t\tborder-radius: 7px 4px 4px 4px;\n\t\t\t\t\tborder-right: 7px solid rgba(255,255,255,0.6);\n\t\t\t\t\tborder-top: 7px solid rgba(255,255,255,0.6);\n\t\t\t\t\theight: 15px;\n\t\t\t\t\twidth: 15px;\n\t\t\t\t\tbackground-color: transparent;\n\t\t\t\t\ttransform: translate(-4px, 4px); \n\t\t\t\t}\n\t\t\t\tcropper-handle[action=\"ne-resize\"]::after {\n\t\t\t\t\tborder-radius: 5px 4px 4px 4px;\n\t\t\t\t\tborder-right: 5px solid #0052CC;\n\t\t\t\t\tborder-top: 5px solid #0052CC;\n\t\t\t\t\theight: 15px;\n\t\t\t\t\twidth: 15px;\n\t\t\t\t\tbackground-color: transparent;\n\t\t\t\t\ttransform: translate(-7px, -14px); \n\t\t\t\t}\n\t\t\t\tcropper-handle[action=\"nw-resize\"] {\n\t\t\t\t\tborder-radius: 4px 7px 4px 4px;\n\t\t\t\t\tborder-left: 7px solid rgba(255,255,255,0.6);\n\t\t\t\t\tborder-top: 7px solid rgba(255,255,255,0.6);\n\t\t\t\t\theight: 15px;\n\t\t\t\t\twidth: 15px;\n\t\t\t\t\tbackground-color: transparent;\n\t\t\t\t\ttransform: translate(4px, 4px); \n\t\t\t\t}\n\t\t\t\tcropper-handle[action=\"nw-resize\"]::after {\n\t\t\t\t\tborder-radius: 4px 5px 4px 4px;\n\t\t\t\t\tborder-left: 5px solid #0052CC;\n\t\t\t\t\tborder-top: 5px solid #0052CC;\n\t\t\t\t\theight: 15px;\n\t\t\t\t\twidth: 15px;\n\t\t\t\t\tbackground-color: transparent;\n\t\t\t\t\ttransform: translate(-14px, -14px); \n\t\t\t\t}\n\t\t\t\tcropper-handle[action=\"se-resize\"] {\n\t\t\t\t\tborder-radius: 4px 4px 7px 4px;\n\t\t\t\t\tborder-right: 7px solid rgba(255,255,255,0.6);\n\t\t\t\t\tborder-bottom: 7px solid rgba(255,255,255,0.6);\n\t\t\t\t\theight: 15px;\n\t\t\t\t\twidth: 15px;\n\t\t\t\t\tbackground-color: transparent;\n\t\t\t\t\ttransform: translate(-4px, -4px); \n\t\t\t\t}\n\t\t\t\tcropper-handle[action=\"se-resize\"]::after {\n\t\t\t\t\tborder-radius: 4px 4px 5px 4px;\n\t\t\t\t\tborder-right: 5px solid #0052CC;\n\t\t\t\t\tborder-bottom: 5px solid #0052CC;\n\t\t\t\t\theight: 15px;\n\t\t\t\t\twidth: 15px;\n\t\t\t\t\tbackground-color: transparent;\n\t\t\t\t\ttransform: translate(-7px, -7px); \n\t\t\t\t}\n\t\t\t\tcropper-handle[action=\"sw-resize\"] {\n\t\t\t\t\tborder-radius: 4px 4px 4px 7px;\n\t\t\t\t\tborder-left: 7px solid rgba(255,255,255,0.6);\n\t\t\t\t\tborder-bottom: 7px solid rgba(255,255,255,0.6);\n\t\t\t\t\theight: 15px;\n\t\t\t\t\twidth: 15px;\n\t\t\t\t\tbackground-color: transparent;\n\t\t\t\t\ttransform: translate(4px, -4px); \n\t\t\t\t}\n\t\t\t\tcropper-handle[action=\"sw-resize\"]::after {\n\t\t\t\t\tborder-radius: 4px 4px 4px 5px;\n\t\t\t\t\tborder-left: 5px solid #0052CC;\n\t\t\t\t\tborder-bottom: 5px solid #0052CC;\n\t\t\t\t\theight: 15px;\n\t\t\t\t\twidth: 15px;\n\t\t\t\t\tbackground-color: transparent;\n\t\t\t\t\ttransform: translate(-14px, -7px); \n\t\t\t\t}\n\t\t\t\t".concat(circularStyle, "\n\t\t\t");
document.head.appendChild(style);
return function () {
return style.remove();
};
}, [isCircle]);
return /*#__PURE__*/_react.default.createElement(CropperCanvas, {
ref: canvasRef,
class: className,
background: background
// eslint-disable-next-line @atlassian/perf-linting/no-unstable-inline-props -- Ignored via go/ees017 (to be fixed)
,
style: {
opacity: isImageReady ? 1 : 0
}
}, /*#__PURE__*/_react.default.createElement(CropperImage, {
ref: imageRef,
src: src,
alt: alt,
crossorigin: crossOrigin,
rotatable: rotatable,
scalable: scalable,
translatable: translatable,
"initial-center-size": "contain"
}), /*#__PURE__*/_react.default.createElement(CropperShade, {
x: 240,
y: 5,
width: 160,
height: 90
}), /*#__PURE__*/_react.default.createElement(CropperSelection, {
ref: selectionRef,
"initial-coverage": initialCoverage,
"aspect-ratio": aspectRatio,
"initial-aspect-ratio": initialAspectRatio,
movable: movable,
resizable: resizable,
zoomable: zoomable,
multiple: multiple,
outlined: outlined
}, /*#__PURE__*/_react.default.createElement(CropperGrid, {
role: "grid",
hidden: true
}), /*#__PURE__*/_react.default.createElement(CropperCrosshair, {
hidden: true
}), /*#__PURE__*/_react.default.createElement(CropperHandle, {
action: "move"
}), /*#__PURE__*/_react.default.createElement(CropperHandle, {
action: "ne-resize"
}), /*#__PURE__*/_react.default.createElement(CropperHandle, {
action: "nw-resize"
}), /*#__PURE__*/_react.default.createElement(CropperHandle, {
action: "se-resize"
}), /*#__PURE__*/_react.default.createElement(CropperHandle, {
action: "sw-resize"
})));
});
Cropper.displayName = 'Cropper';