Qlik Sense mashups can be quite simple at first. The dev hub lets you create the files you need, connect to and app and drop in charts.
Here’s a simple example on how load three charts (hide two) then toggle between them using CSS and JavaScript.
<!doctype html> <html><head> <meta http-equiv="X-UA-Compatible" content="IE=edge,chrome=1"> <title>Qlik Sense Mashup</title> <meta charset="utf-8"> <meta http-equiv="content-type" content="text/html; charset=UTF-8"> <meta name="HandheldFriendly" content="True"> <meta name="MobileOptimized" content="320"> <meta name="viewport" content="width=device-width, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0, user-scalable=no"> <meta name="apple-mobile-web-app-capable" content="yes"> <meta name="apple-mobile-web-app-status-bar-style" content="black"> <meta http-equiv="cleartype" content="on"> <link rel="stylesheet" href="../../resources/autogenerated/qlik-styles.css"> <script src="../../resources/assets/external/requirejs/require.js"></script> <link href="https://cdn.jsdelivr.net/npm/bootstrap@5.0.2/dist/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-EVSTQN3/azprG1Anm3QDgpJLIm9Nao0Yz1ztcQTwFspd3yD65VohhpuuCOmLASjC" crossorigin="anonymous"> <script> var prefix = window.location.pathname.substr( 0, window.location.pathname.toLowerCase().lastIndexOf( "/extensions" ) + 1 ); var config = { host: window.location.hostname, prefix: prefix, port: window.location.port, isSecure: window.location.protocol === "https:" }; require.config( { baseUrl: ( config.isSecure ? "https://" : "http://" ) + config.host + (config.port ? ":" + config.port : "") + config.prefix + "resources" } ); require( ["js/qlik"], function ( qlik ) { console.log("Internal Script") qlik.setOnError(function(error) { alert(error.message); }); var appName = 'YOURDASHBORD.qvf'; // Update to your Dashboard name console.log("App Script") app = qlik.openApp (appName , config); $(".qlik_resize").click(function() { qlik.resize();}); app.getObject('QV01','BYyyYB'); // Update to your object ID app.getObject('QV02','BsCae'); // Update to your object ID app.getObject('QV03','aZAYGg'); // Update to your object ID's myToggleShowHide('QV01'); // This shows the first chart and hides the second two }); function myToggleShowHide(myID) { // Sure this can be improved so it more reusable but its good enough for now console.log(myID) ; if (myID === "QV03") { document.getElementById("QV04").style.display = "none" document.getElementById("QV05").style.display = "none" document.getElementById("QV03").style.display = "block" } else if (myID === "QV04") { document.getElementById("QV03").style.display = "none" document.getElementById("QV05").style.display = "none" document.getElementById("QV04").style.display = "block" } else if (myID === "QV05") { document.getElementById("QV03").style.display = "none" document.getElementById("QV04").style.display = "none" document.getElementById("QV05").style.display = "block" } }; </script> </head> <body style="overflow: auto"> <div class="row"> <div class="btn-group" role="group" aria-label="Basic radio toggle button group"> <input onclick="myToggleShowHide('QV01')" type="radio" class="btn-check" name="btnradio" id="btnradio1" autocomplete="off" checked> <label class="btn btn-outline-primary qlik_resize" for="btnradio1">Radio 1</label> <input onclick="myToggleShowHide('QV02')" type="radio" class="btn-check" name="btnradio" id="btnradio2" autocomplete="off"> <label class="btn btn-outline-primary qlik_resize" for="btnradio2">Radio 2</label> <input onclick="myToggleShowHide('QV03')" type="radio" class="btn-check" name="btnradio" id="btnradio3" autocomplete="off"> <label class="btn btn-outline-primary qlik_resize" for="btnradio3">Radio 3</label> </div> </div> <div class="row my-row"> <div id="QV03" class="qvobject"></div> <div id="QV02" class="qvobject"></div> <div id="QV03" class="qvobject"></div> </div> </div> <!--Error Popup--> <div id="popup"> <button type="button" class="close" data-dismiss="modal" aria-label="Close" id="closePopup"><span aria-hidden="true">×</span></button> <p id="popupText"></p> </div> </body>
Lots going on here so lets break it down… in the main Qlik function we get three objects (charts) which we display in the HTML (below):
<div class="row my-row"> <div id="QV03" class="qvobject"></div> <div id="QV02" class="qvobject"></div> <div id="QV03" class="qvobject"></div> </div>
We also have three buttons (bootstrap). Each button calls the same function and passes the ID of the Qlik object to it:
<input onclick="myToggleShowHide('QV01')" type="radio" class="btn-check" name="btnradio" id="btnradio1" autocomplete="off" checked> <label class="btn btn-outline-primary qlik_resize" for="btnradio1">Radio 1</label>
The function picks up the ID then by changing the CSS style display property shows (block) or hides (none) the object…
function myToggleShowHide(myID) { // Sure this can be improved so it more reusable but its good enough for now console.log(myID) ; if (myID === "QV01") { document.getElementById("QV01").style.display = "block" document.getElementById("QV02").style.display = "none" document.getElementById("QV03").style.display = "none" } else if (myID === "QV02") { document.getElementById("QV01").style.display = "none" document.getElementById("QV02").style.display = "block" document.getElementById("QV03").style.display = "none" } else if (myID === "QV03") { document.getElementById("QV01").style.display = "none" document.getElementById("QV02").style.display = "none" document.getElementById("QV03").style.display = "block" } };
Finally in order for Qlik to recalculate the charts when they become visible you need to resize them, this is done using a callback in the main Qlik function which listens to the class of “qlik_resize” each button shares (highlighted in green above).
$(".qlik_resize").click(function() { qlik.resize();});