Expand my Community achievements bar.

Don’t miss the AEM Skill Exchange in SF on Nov 14—hear from industry leaders, learn best practices, and enhance your AEM strategy with practical tips.
SOLVED

Set default crop aspect ratio on html5smartimage

Avatar

Level 2

I have succesfully changed the aspectRatioConfig for a html5smartimage component to replace the default "Free crop" with a custom aspect ratio, however I'm struggling to find a way to select my custom aspect ratio as the default selection when cropping images. Essentially, I want to default to my custom aspect ratio rather than have the user select this from the list of aspect ratios (in this case there is only one value). Is this possible? Can anyone assist?

here is my code to replace the free crop, with my custom config, I was thinking that setting the checked value of the available aspect ratios (in initConfig below) would trigger the selected event, but it doesn't appear too. How can I default the selected aspect ratio ? Or perhaps trigger the selected event ?

(function($, undefined) {/**     * Determine the scaling ratio the image component might have applied     *     * @param data contains `imgWidth` and `imgHeight` keys     * @returns {number} is the scaling ratio, 1 if no scaling was applied.     */    function getScalingRatio(data) {var scaleRatio = 1;if (data.imgWidth > 1280 || data.imgHeight > 1280) {if (data.imgWidth > 1280) {scaleRatio = 1280 / data.imgWidth; } else {scaleRatio = 1280 / data.imgHeight; } }return scaleRatio; }/**     * Wrapper for the HTML5 aspect ratio aware     *     * @type {void|*}     */    window.CQTG = $.extend(window.CQTG || {}, {Html5SmartImageWrapper: CQ.Ext.extend(CQ.Ext.Panel, {/**             * Initialize panel             *             * @param originalConfig             */            constructor: function (originalConfig) {// initialize the container so we get some useful information                CQTG.Html5SmartImageWrapper.superclass.constructor.call(this, $.extend({}, originalConfig, {layout: 'fit',bodyStyle: 'padding: 0;',items: {title: null,header: false,frameHeader: false,border: false                    } }));// find the data path for this container instance                originalConfig.imagePath = this.findParentByType('dialog').responseScope.path;// get rid of panel and replace with smart image                this.removeAll();// add add html5 smart image to the container                this.add(new CQTG.Html5SmartImage(originalConfig)); } }),Html5SmartImage: CQ.Ext.extend(CQ.html5.form.SmartImage, {/**             * Initialize data-members             *             * @param config             */            constructor: function (config) { config = config || {};var aInfo = this.getAspectRatioString(config.imagePath);// setup some default values                config = CQ.Util.applyDefaults(config, {"cropConfig": {"aspectRatios": {"newsholeCrop": {"text": "Newshole crop","value": aInfo.aspectRatio                                } } } } );CQTG.Html5SmartImage.superclass.constructor.call(this, config);// first tool is the crop (rest has been disabled)                this.imageToolDefs[0].cropMinWidth = aInfo.minWidth;this.imageToolDefs[0].cropMinHeight = aInfo.minHeight; },/**             * Retrieve the bounding box and concoct a aspect ratio based on it             *             * There is some additional magic here because the image component uses a rendition,             * not the original and bases all its pixel calculations on it without scaling it back             * up. That is why the scaleRatio is determined             */            getAspectRatioString: function (cmpPath) {var                    boundingBoxLocation = cmpPath.substring(0, cmpPath.lastIndexOf('/')),data = CQ.Util.eval(boundingBoxLocation + ".crop.json"),roundX = Math.ceil(data.aspectX * 100),roundY = Math.ceil(data.aspectY * 100),scaleRatio = getScalingRatio(data) ;return {aspectRatio: (roundX + "," + roundY),minWidth: Math.ceil(data.minCropWidth * scaleRatio),minHeight: Math.ceil(data.minCropHeight * scaleRatio) }; },initComponent: function () {CQTG.Html5SmartImage.superclass.initComponent.call(this);var cropTool = null;CQ.Ext.each(this.imageToolDefs, function(tool){if(tool.toolId == "smartimageCrop"){cropTool = tool; } });var userInterface = cropTool.userInterface;this.on("loadimage", function(){var aRatios = userInterface.aspectRatioMenu.findByType("menucheckitem");if(!aRatios[0].checked || !aRatios[0].initialConfig.checked){aRatios[0].checked = true;aRatios[0].initialConfig.checked = true; } }); } }) });CQ.Ext.reg("ffx.html5smartimage", CQTG.Html5SmartImageWrapper); })($CQ);
1 Accepted Solution

Avatar

Correct answer by
Level 2

Sorted this out myself.....I actually wasn't too far off when I posted this initially. I just needed to find the correct event to trigger the aspectRatio update. Turns out to be I needed to override smartImage.js toolClicked() method and reset the aspectRatio via setAspectRatioUI, then re-trigger onRatioChanged

(function($, undefined) { /** * Determine the scaling ratio the image component might have applied * * @param data contains `imgWidth` and `imgHeight` keys * @returns {number} is the scaling ratio, 1 if no scaling was applied. */ function getScalingRatio(data) { var scaleRatio = 1; if (data.imgWidth > 1280 || data.imgHeight > 1280) { if (data.imgWidth > 1280) { scaleRatio = 1280 / data.imgWidth; } else { scaleRatio = 1280 / data.imgHeight; } } return scaleRatio; } /** * Wrapper for the HTML5 aspect ratio aware * * @type {void|*} */ window.CQTG = $.extend(window.CQTG || {}, { Html5SmartImageWrapper: CQ.Ext.extend(CQ.Ext.Panel, { /** * Initialize panel * * @param originalConfig */ constructor: function (originalConfig) { // initialize the container so we get some useful information CQTG.Html5SmartImageWrapper.superclass.constructor.call(this, $.extend({}, originalConfig, { layout: 'fit', bodyStyle: 'padding: 0;', items: { title: null, header: false, frameHeader: false, border: false } })); // find the data path for this container instance originalConfig.imagePath = this.findParentByType('dialog').responseScope.path; // get rid of panel and replace with smart image this.removeAll(); // add add html5 smart image to the container this.add(new CQTG.Html5SmartImage(originalConfig)); } }), Html5SmartImage: CQ.Ext.extend(CQ.html5.form.SmartImage, { /** * Initialize data-members * * @param config */ constructor: function (config) { config = config || {}; var aInfo = this.getAspectRatioString(config.imagePath); // setup some default values config = CQ.Util.applyDefaults(config, { "cropConfig": { "aspectRatios": { "newsholeCrop": { "text": "Newshole crop", "value": aInfo.aspectRatio, "checked": true } } } } ); CQTG.Html5SmartImage.superclass.constructor.call(this, config); // first tool is the crop (rest has been disabled) this.imageToolDefs[0].cropMinWidth = aInfo.minWidth; this.imageToolDefs[0].cropMinHeight = aInfo.minHeight; }, /** * Retrieve the bounding box and concoct a aspect ratio based on it * * There is some additional magic here because the image component uses a rendition, * not the original and bases all its pixel calculations on it without scaling it back * up. That is why the scaleRatio is determined */ getAspectRatioString: function (cmpPath) { var boundingBoxLocation = cmpPath.substring(0, cmpPath.lastIndexOf('/')), data = CQ.Util.eval(boundingBoxLocation + ".crop.json"), roundX = Math.ceil(data.aspectX * 100), roundY = Math.ceil(data.aspectY * 100), scaleRatio = getScalingRatio(data) ; return { aspectRatio: (roundX + "," + roundY), minWidth: Math.ceil(data.minCropWidth * scaleRatio), minHeight: Math.ceil(data.minCropHeight * scaleRatio) }; }, /** * override smartImage toolClicked and set default cropTool to "Newshole crop" */ toolClicked: function(cropTool) { cropTool = null; CQ.Ext.each(this.imageToolDefs, function(tool){ if(tool.toolId == "smartimageCrop"){ cropTool = tool; } }); CQTG.Html5SmartImage.superclass.toolClicked.call(this, cropTool); var userInterface = cropTool.userInterface; var aRatios = userInterface.aspectRatioMenu.findByType("menucheckitem"); if(!aRatios[0].checked){ aRatios[0].checked = true; } userInterface.setAspectRatioUI(aRatios[0].value); userInterface.onRatioChanged(aRatios[0].value, aRatios[0].text); } }) }); CQ.Ext.reg("ffx.html5smartimage", CQTG.Html5SmartImageWrapper); })($CQ);

View solution in original post

5 Replies

Avatar

Level 2

Neither of those links address the problem I've posted. i have already changed the configuration to remove the "free crop" aspect ratio and added my own configuration. What i want to do is have my custom aspect ratio default to the selected aspect ratio, rather than the user need to select it.

Avatar

Level 7

In that case you could use image transformer to address this issue of yours.

Here is a similar kind of problem posted earlier in the community, this might be of your help

http://help-forums.adobe.com/content/adobeforums/en/experience-manager-forum/adobe-experience-manage...

 

Thanks

Tuhin

Avatar

Correct answer by
Level 2

Sorted this out myself.....I actually wasn't too far off when I posted this initially. I just needed to find the correct event to trigger the aspectRatio update. Turns out to be I needed to override smartImage.js toolClicked() method and reset the aspectRatio via setAspectRatioUI, then re-trigger onRatioChanged

(function($, undefined) { /** * Determine the scaling ratio the image component might have applied * * @param data contains `imgWidth` and `imgHeight` keys * @returns {number} is the scaling ratio, 1 if no scaling was applied. */ function getScalingRatio(data) { var scaleRatio = 1; if (data.imgWidth > 1280 || data.imgHeight > 1280) { if (data.imgWidth > 1280) { scaleRatio = 1280 / data.imgWidth; } else { scaleRatio = 1280 / data.imgHeight; } } return scaleRatio; } /** * Wrapper for the HTML5 aspect ratio aware * * @type {void|*} */ window.CQTG = $.extend(window.CQTG || {}, { Html5SmartImageWrapper: CQ.Ext.extend(CQ.Ext.Panel, { /** * Initialize panel * * @param originalConfig */ constructor: function (originalConfig) { // initialize the container so we get some useful information CQTG.Html5SmartImageWrapper.superclass.constructor.call(this, $.extend({}, originalConfig, { layout: 'fit', bodyStyle: 'padding: 0;', items: { title: null, header: false, frameHeader: false, border: false } })); // find the data path for this container instance originalConfig.imagePath = this.findParentByType('dialog').responseScope.path; // get rid of panel and replace with smart image this.removeAll(); // add add html5 smart image to the container this.add(new CQTG.Html5SmartImage(originalConfig)); } }), Html5SmartImage: CQ.Ext.extend(CQ.html5.form.SmartImage, { /** * Initialize data-members * * @param config */ constructor: function (config) { config = config || {}; var aInfo = this.getAspectRatioString(config.imagePath); // setup some default values config = CQ.Util.applyDefaults(config, { "cropConfig": { "aspectRatios": { "newsholeCrop": { "text": "Newshole crop", "value": aInfo.aspectRatio, "checked": true } } } } ); CQTG.Html5SmartImage.superclass.constructor.call(this, config); // first tool is the crop (rest has been disabled) this.imageToolDefs[0].cropMinWidth = aInfo.minWidth; this.imageToolDefs[0].cropMinHeight = aInfo.minHeight; }, /** * Retrieve the bounding box and concoct a aspect ratio based on it * * There is some additional magic here because the image component uses a rendition, * not the original and bases all its pixel calculations on it without scaling it back * up. That is why the scaleRatio is determined */ getAspectRatioString: function (cmpPath) { var boundingBoxLocation = cmpPath.substring(0, cmpPath.lastIndexOf('/')), data = CQ.Util.eval(boundingBoxLocation + ".crop.json"), roundX = Math.ceil(data.aspectX * 100), roundY = Math.ceil(data.aspectY * 100), scaleRatio = getScalingRatio(data) ; return { aspectRatio: (roundX + "," + roundY), minWidth: Math.ceil(data.minCropWidth * scaleRatio), minHeight: Math.ceil(data.minCropHeight * scaleRatio) }; }, /** * override smartImage toolClicked and set default cropTool to "Newshole crop" */ toolClicked: function(cropTool) { cropTool = null; CQ.Ext.each(this.imageToolDefs, function(tool){ if(tool.toolId == "smartimageCrop"){ cropTool = tool; } }); CQTG.Html5SmartImage.superclass.toolClicked.call(this, cropTool); var userInterface = cropTool.userInterface; var aRatios = userInterface.aspectRatioMenu.findByType("menucheckitem"); if(!aRatios[0].checked){ aRatios[0].checked = true; } userInterface.setAspectRatioUI(aRatios[0].value); userInterface.onRatioChanged(aRatios[0].value, aRatios[0].text); } }) }); CQ.Ext.reg("ffx.html5smartimage", CQTG.Html5SmartImageWrapper); })($CQ);