advanced-cropper / vue-advanced-cropper

The advanced vue cropper library that gives you opportunity to create your own croppers suited for any website design
https://advanced-cropper.github.io/vue-advanced-cropper/
Other
1k stars 136 forks source link

Saving/Retrieving cropper settings to re-apply at a later time #268

Closed leonwisdom closed 9 months ago

leonwisdom commented 9 months ago

I need to be able to store the cropper config settings, to use them again later i.e a user wants to go back a step and need to load the last known settings (coordinates, visibleArea etc) for each cropper.

The code below isn't exact but it shows what i'm trying to achieve.

const croppers = [];
const cropperConfigs = [];

const cropperRef = el => {
    // Save cropper instance if it doesn't exist
    if (el && !croppers.includes(el)) {
        croppers.push(el);
    }
}

const saveCropperConfig = (cropper) => {
    if (cropper) {
        // deconstruct cropper
        const { visibleArea, $attrs: { customCropperId }, boundaries, coordinates, stencilCoordinates } = cropper;

        cropperConfigs.push({
            customCropperId: customCropperId,
            // Save other cropper settings into config array
            visibleArea: { ...visibleArea },
            boundaries: { ...boundaries },
            coordinates: { ...coordinates },
            stencilCoordinates: { ...stencilCoordinates },
        });
    }
};

const retrieveCropperConfig = (customCropperId) => {
    // find cropper config by customCropperId
    const cropperConfig = cropperConfigs.find((conf) => conf.customCropperId === customCropperId);

    if(cropperConfig) {
        // find cropper by customCropperId
        const cropper = croppers.find((cropper) => cropper.$attrs.imageId === cropperConfig.customCropperId);

        // deconstruct cropper config
        const { visibleArea, boundaries, coordinates, stencilCoordinates } = cropperConfig;
        const { height, width } = visibleArea;

        // apply last known cropper settings
        cropper.visibleArea = { ...visibleArea, height, width };
        cropper.boundaries = { ...boundaries };
        cropper.setCoordinates({ ...coordinates });
        cropper.stencilCoordinates = { ...stencilCoordinates };
        cropper.update();
    }
};

const ready = (cropperId) => {
    const cropper = croppers.find((cropper) => cropper.$attrs.customCropperId === cropperId);

    if (cropper) {
        console.log('ready retrieving cropper: ' + cropperId)
        retrieveCropperConfig(cropper);
    }
}

const onChange = (cropperId) => {
    const cropper = croppers.find((cropper) => cropper.$attrs.customCropperId === cropperId);

    if (cropper) {
        console.log('onChange saving cropper: ' + cropperId)
        saveCropperConfig(cropper);
    }
}

<Cropper @ready="ready(image.id)" :key="index"
    :ref="cropperRef" :src="image.path" :customCropperId="image.id" :sort="index"
    default-boundaries="fill" image-restriction="stencil" @change="onChange(image.id)">
</Cropper>

I don't know if its possible but i'm trying to get it working. I haven't found anything that could help in the docs, so i thought i would reach out here. Has any one had a need to do this, know how or could share a solution or advice?

leonwisdom commented 9 months ago

I found the problem to the issues i was having.

Another component i have wasn't retrieving the cropper coordinates after i updated the images array on the carousel. I also add the code below to my retrieveCropperConfig function and now when i step back in the form process, the saved cropper coordinates now get applied.

const { width, height, left, top } = cropperConfig.coordinates;

cropper.setCoordinates({
    width: width,
    height: height,
    left: left,
    top: top
})

cropper.move(left, top);