The applyForceCrop API allows you to programmatically apply a crop preset to a specific design block, typically a page. This is useful in scenarios where you want to enforce a particular format (e.g., fixed aspect ratio) and define how the editor should respond after the preset is applied.
Overview#
You can use applyForceCrop to apply predefined crop presets to a block that supports cropping, such as a page. The API automatically selects the best matching preset from the candidates you provide based on the block’s current dimensions. You can provide multiple preset candidates, and the system will intelligently choose the most appropriate one.
The API provides flexible behavior through the mode parameter, controlling whether the crop UI is shown and whether cropping is conditionally applied based on the block’s current dimensions.
This API is available as an event context.eventHandler.send(.applyForceCrop(...)) within the .imgly.onLoaded callback.
context.eventHandler.send(.applyForceCrop( to blockID: DesignBlockID, with presetCandidates: [ForceCropPreset], mode: ForceCropMode))Parameters#
| Name | Type | Description |
|---|---|---|
blockID | DesignBlockID | The ID of the block you want to apply the crop to. Must support cropping. |
presetCandidates | [ForceCropPreset] | Array of crop preset candidates. The best matching preset will be automatically selected. |
mode | ForceCropMode | Defines how the UI should behave after applying the crop. See below. |
ForceCropPreset#
Each preset candidate requires:
| Property | Type | Description |
|---|---|---|
sourceID | String | ID of the asset source where the crop preset exists |
presetID | String | ID of the crop preset within that source |
Modes#
| Mode | Behavior |
|---|---|
.silent | Applies the preset without opening the crop UI. |
.always | Applies the preset and always switches to crop mode in the UI. |
.ifNeeded | Only applies the preset if the block’s current dimensions or aspect ratio differ from the preset. Switches to crop mode only if a change is made. |
Usage Example#
The example shows how to apply a custom crop preset when the editor loads.
Creating the Preset#
// Create a custom 1:1 aspect ratio presetlet preset = AssetDefinition( id: "custom-preset-1-1", payload: .init( transformPreset: .fixedAspectRatio(width: 1, height: 1), ), label: ["en": "Square"],)First, define a custom AssetDefinition with the desired aspect ratio.
Setting Up the Source#
// Isolate the forced preset in the sourcelet sourceID = Engine.DefaultAssetSource.pagePresets.rawValuetry context.engine.asset.removeSource(sourceID: sourceID)try context.engine.asset.addLocalSource(sourceID: sourceID)try context.engine.asset.addAsset(to: sourceID, asset: preset)If you’re using a demo source that contains existing presets, remove it first to start with a clean slate. Otherwise, you can add crop presets directly to your own source.
Applying Force Crop#
// Apply force cropcontext.eventHandler.send(.applyForceCrop( to: page, with: [ForceCropPreset(sourceID: sourceID, presetID: preset.id)], mode: .always,))Use the .applyForceCrop event with .always mode to apply the preset and open the crop UI.
Working with Asset Sources#
You can add multiple crop presets to an asset source. The force crop API works with any valid preset in the specified source.
Using a Demo Source#
If you’re working with a demo source that already contains presets, you may want to remove it first to avoid unwanted presets appearing in the crop options UI:
let sourceID = "ly.img.page.presets"try context.engine.asset.removeSource(sourceID: sourceID)try context.engine.asset.addLocalSource(sourceID: sourceID)try context.engine.asset.addAsset(to: sourceID, asset: yourPreset)Using Your Own Source#
If you’re using your own custom source, you can add crop presets directly without removing anything:
let sourceID = "my.custom.source"try context.engine.asset.addLocalSource(sourceID: sourceID)try context.engine.asset.addAsset(to: sourceID, asset: firstPreset)try context.engine.asset.addAsset(to: sourceID, asset: secondPreset)// Add as many presets as neededThis allows you to provide multiple crop options while still using force crop to programmatically apply specific presets.
Best Match Selection#
When you provide multiple preset candidates, the system automatically selects the best match based on how closely each preset matches the block’s current dimensions:
- For fixed aspect ratio presets: Calculates the difference between the block’s aspect ratio and the preset’s aspect ratio
- For fixed size presets: Calculates the total dimensional difference after harmonizing units
- For free aspect ratio presets: These receive the lowest priority
The preset with the smallest difference (best fit) is automatically selected and applied.
Behavior Details#
applyForceCropbypasses the usual user interaction required to apply crop presets manually.- When multiple preset candidates are provided, the best matching preset is automatically selected based on the block’s current dimensions.
- When used in
.alwaysor.ifNeededmode, the crop UI is automatically opened (if appropriate). - Invalid
presetIDorsourceIDvalues in the candidates are silently skipped. At least one valid preset must be found. - The block must be valid and support cropping, otherwise an error is thrown.