hybris: Display Popup with custom HTML in Backoffice
by admin on Feb.20, 2019, under Programming
This tutorial will guide you through the necessary steps of creating an action triggered popup in Backoffice containing custom HTML/CSS/JavaScript. The result will look alike:
Assuming you did setup hybris via one of the available recipes you should already have a backoffice extension in hybris/bin/custom/. For a project called ‘tomato‘ we’d have an extension called tomatobackoffice.
Creating a new Backoffice action
Create the following directory structure: tomatobackoffice/backoffice/resources/widgets/actions/testpreview/
In the ‘testpreview‘ directory, create a subdirectory called ‘icons‘ containing the action icons and put some icon files in there.
In the ‘testpreview‘ directory, create a file called ‘definition.xml‘ containing an action definition:
<?xml version="1.0" encoding="UTF-8"?> <action-definition xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" id="us.betamaster.tomato.backoffice.widgets.actions.testpreview" xsi:noNamespaceSchemaLocation="http://www.hybris.com/schema/cockpitng/action-definition.xsd"> <sockets> <output id="currentObject" type="de.hybris.platform.core.model.ItemModel"/> </sockets> <name>Test Preview</name> <description>Toolbar action displaying a preview popup</description> <version>1.0</version> <iconUri>icons/tomato_enabled.png</iconUri> <iconHoverUri>icons/tomato_hover.png</iconHoverUri> <iconDisabledUri>icons/tomato_disabled.png</iconDisabledUri> <actionClassName>us.betamaster.tomato.backoffice.widgets.actions.testpreview.TestPreviewAction</actionClassName> <view src="testpreview.zul" /> </action-definition>
Inside definition.xml we’re utilising the icon files we copied into the ‘icons‘ subdirectory in the previous step.
In the ‘testpreview’ directory, create a file called ‘testpreview.zul’
<window title="Preview" width="80%" border="normal" closable="true" sizable="true"> <vlayout style="margin: 20px; overflow: auto;"> <hbox style="position: fixed;"> The code below will appear highlighted: </hbox> <hbox width="100%" style="overflow: scroll; margin-top: 20px;"> <html> <link rel="stylesheet" href="/backoffice/widgetClasspathResource/widgets/actions/testpreview/css/default.min.css" async="false" /> <script src="/backoffice/widgetClasspathResource/widgets/actions/testpreview/js/highlight.site.pack.js" async="false" /> <pre><code class="xml" style="overflow: scroll; word-wrap: break-word;background: transparent;">${arg.testExport}</code></pre> <script type="text/javascript"> document.querySelectorAll('pre code').forEach((block) => { hljs.highlightBlock(block); }); </script> </html> </hbox> </vlayout> </window>
The zul file will take a passed argument called ‘xml’ from a controller and render it. Furthermore, we embedded some CSS and JS from a library called highlight.js in order to apply syntax highlighting.
Next we’re going to implement the TestPreviewAction in Java:
Create the directory structure and file: tomatobackoffice/backoffice/src/us/betamaster/backoffice/widgets/actions/testpreview/TestPreviewAction.java
package us.betamaster.tomato.backoffice.widgets.actions.testpreview; import com.hybris.cockpitng.actions.ActionContext; import com.hybris.cockpitng.actions.ActionResult; import com.hybris.cockpitng.actions.CockpitAction; import com.hybris.cockpitng.engine.impl.AbstractComponentWidgetAdapterAware; import de.hybris.platform.core.model.order.AbstractOrderModel; import de.hybris.platform.core.model.order.OrderModel; import org.apache.commons.lang.StringEscapeUtils; import org.zkoss.zk.ui.Executions; import org.zkoss.zk.ui.util.Clients; import org.zkoss.zul.Window; import javax.annotation.Resource; import java.util.Collections; import java.util.List; public class TestPreviewAction extends AbstractComponentWidgetAdapterAware implements CockpitAction<Object, List> { protected static final String SOCKET_OUT_SELECTED_OBJECTS = "currentObject"; @Override public ActionResult<List> perform(ActionContext<Object> actionContext) { if(actionContext.getData() != null) { this.sendOutput("currentObject", actionContext.getData()); String xml = " <?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" + "<note>\n" + " <to>Tove</to>\n" + " <from>Jani</from>\n" + " <heading>Reminder</heading>\n" + " <body>Don't forget me this weekend!</body>\n" + "</note> "; // Escape the XML content in preparation for the ZUL file xml = StringEscapeUtils.escapeHtml(xml); String template = "/widgets/actions/testpreview/testpreview.zul"; Window window = (Window) Executions.createComponents(template, null, Collections.singletonMap("xml", xml)); window.doModal(); return new ActionResult("success"); } return new ActionResult("error"); } @Override public boolean canPerform(ActionContext<Object> ctx) { return ctx.getData() instanceof AbstractOrderModel; } @Override public boolean needsConfirmation(ActionContext<Object> ctx) { return false; } @Override public String getConfirmationMessage(ActionContext<Object> ctx) { return null; } }
Last but not least we’re going to extend the file tomatobackoffice-backoffice-config.xml in order to use our newly defined action:
<context type="AbstractOrder" component="editorareaactions" merge-by="type" parent="auto"> <y:actions xmlns:y="http://www.hybris.com/cockpit/config/hybris"> <y:group qualifier="common"> <y:action action-id="us.betamaster.tomato.backoffice.widgets.actions.testpreview" property="currentObject"/> </y:group> </y:actions> </context>
After reloading the Backoffice config a new toolbar button appears for Orders and clicking it will reveal our new dialog window: