I am building a relatively straight-forward AEM component with a simple authoring dialog. At the top of my dialog is a select field. I want certain fields in my dialog to disappear when this select field is set to a specific item.
I have studied the implementation of the Foundation Carousel component, which uses the cq-dialog-dropdown-showhide-target
attribute, which is fine, but isn't quite the logic I am looking for. The logic used there is:
show this field if the select is equal to X
Whereas I am trying to implement:
hide this field if the select is equal to X, Y or Z, otherwise show it
Has anyone else had trouble implementing this kind of logic in their dialogs?
Thank you in advance!
Dave
Add the a cq-dialog-dropdown-showhide-target property of type String to the granite:data node. The value of this property can be whatever you want, I've opted for . productType-showhide-target. Basically here you're providing a CSS selector to target the fields to show or hide.
Basically idea is on the dropdown field, add a class cq-dialog-dropdown-showhide and a property cq-dialog-dropdown-showhide-target with a value of class selector unique to component. Then by defining property showhidetargetvalue on the element, selecting the dropdown will show/hide respective properties.
It's pretty easy - just add property hidden with boolean value true for jcr:content node of page - and it will be hidden in both tree and grid.
For TouchUI dialogs there is actually no plugin registry that was heavily used in ExtJS framework. This time, we can actually do all the magic with the use of just clientlibs and jQuery.
Take a look at the base implementation that you are refering to that can be found here: /libs/cq/gui/components/authoring/dialog/dropdownshowhide/clientlibs/dropdownshowhide.js
This is a clientlibs that is attached to cq.authoring.dialog
category and requires granite.jquery
to be initialized before. See clientlibs documentation to learn more about it. The script itself is a anonymous function that is invoked with a document parameter and jQuery from granite (see last line in the script: })(document,Granite.$);
)
If given functionality is not sufficent for you, you can create your own clientlib with a similar simple javascript function that will handle more sophisticated conditions. Please also note, that any attribute placed in the "widget" node will be placed as data attribute in resulting html.
For the node (e.g. /libs/foundation/components/carousel/cq:dialog/content/items/list/items/column/items/orderBy
) that you want to hide when some condition occurs place property: hideWhen=children,search (don't make it an array as it won't be properly casted to a string in JS). Point a dropdown selector (/libs/foundation/components/carousel/cq:dialog/content/items/list/items/column/items/listForm@cq-dialog-dropdown-hidefor-target
) to a proper class that you will on the other hand assign to your hideable field.
|-listFrom(select)
| |--@cq-dialog-dropdown-hidefor-target=.orderByClass
|
orderBy(autocomplete)
|--@hideFor=children,search
|--@class=orderByClass
The javascript method for your case could look something like that:
(function(document, $) {
"use strict";
// when dialog gets injected
$(document).on("foundation-contentloaded", function(e) {
// if there is already an inital value make sure the according target element becomes visible
showHide($(".cq-dialog-dropdown-showhide", e.target)) ;
});
$(document).on("selected", ".cq-dialog-dropdown-showhide", function(e) {
showHide($(this));
});
function showHide(el){
var widget = el.data("select");
if (widget) {
// get the selector to find the target elements. its stored as data-.. attribute
var target = el.data("cqDialogDropdownHideforTarget");
// get the selected value
var value = widget.getValue();
// make sure all unselected target elements are hidden.
var hideFor = $(target).data('hidefor').split(',');
$(target).not(".hide").addClass("hide");
// unhide the target element that contains the selected value as data-showhidetargetvalue attribute
if (hideFor.indexOf(value) == -1) {
$(target).removeClass("hide");
}
}
}
There are some issues with hiding input labels in such case so it might be good idea to wrap the field into the section (granite/ui/components/foundation/well)
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With