In the example below we use multiple conditions for filtering(text search, filter by ticket status, filter by ticket public tags, filter based on ticket creation date, ticket resolved date and ticket changed date). You don't need to use all of these filters if you don't want to, but you will need to adjust the example My tickets custom menu HTML code to match your exact needs. This implementation consists of few steps. We will need to define HTML code of the custom filter itself, then we will need to add some custom CSS to make it look better and also include some 3rd party scripts for the functionality.
After you add the custom ticket filter, your customers/visitors will be able to find it on the "My tickets" tab in your LiveAgent customer portal. This tab is visible only for the logged in users. If you use the exact codes mentioned below, the final filter will look like this:
<div class="panel panel-default margin-top margin-bottom"> <div class="panel-heading"> {if !isset($code) || $code == ""} Ticket Filters {elseif $code != ""} <a href="#" onclick="window.history.back();">Back to Ticket Filters</a> {/if} </div> {if !isset($code) || $code == ""} <div class="panel-body"> <div class="filter-body"> <div class="filter_label"></div> <input type="text" id="filterQuery" name="filterQuery" value="{$query|escape}" placeholder="Search text" /> </div> <div class="filter-body"> <div class="filter_label">Status</div> <select class="status-select" name="status"> <option value="A" {if $status == "A"}selected{/if}>Any</option> <option value="O" {if $status == "O"}selected{/if}>Open</option> <option value="AN" {if $status == "AN"}selected{/if}>Answered</option> <option value="RD" {if $status == "RD"}selected{/if}>Resolved</option> </select> </div> <div class="filter-body"> <div class="filter_label">Tags</div> <select class="tags-select" name="tags[]" multiple="multiple"> {foreach from=$publicTags item="tag" key="tag_id"} <option value="{$tag_id}" {if $selectedTags.$tag_id.name > ""}selected{/if} style="color:#{$tag.color}; background-color:#{$tag.backgroundcolor};">{$tag.name}</option> {/foreach} </select> </div> <div class="filter-body"> <div class="filter_label">Created date</div> <div class="dateFilter input-group"> <input id="createdFromInput" class="form-control" placeholder="from RRRR-MM-DD" value="{$createdFrom}"> <div id="createdFrom"></div> <div class="input-group-btn"><button id="createdFromToggle" class="btn btn-default glyphicon glyphicon-calendar"></button></div> </div> <div class="dateFilter input-group"> <input id="createdToInput" class="form-control" placeholder="to RRRR-MM-DD" value="{$createdTo}"> <div id="createdTo"></div> <div class="input-group-btn"><button id="createdToToggle" class="btn btn-default glyphicon glyphicon-calendar"></button></div> </div> </div> <div class="filter-body"> <div class="filter_label">Changed date</div> <div class="dateFilter input-group"> <input id="changedFromInput" class="form-control" placeholder="from RRRR-MM-DD"> <div id="changedFrom"></div> <div class="input-group-btn"><button id="changedFromToggle" class="btn btn-default glyphicon glyphicon-calendar"></button></div> </div> <div class="dateFilter input-group"> <input id="changedToInput" class="form-control" placeholder="to RRRR-MM-DD"> <div id="changedTo"></div> <div class="input-group-btn"><button id="changedToToggle" class="btn btn-default glyphicon glyphicon-calendar"></button></div> </div> </div> <div class="filter-body"> <div class="filter_label">Resolved date</div> <div class="dateFilter input-group"> <input id="resolvedFromInput" class="form-control" placeholder="from RRRR-MM-DD"> <div id="resolvedFrom"></div> <div class="input-group-btn"><button id="resolvedFromToggle" class="btn btn-default glyphicon glyphicon-calendar"></button></div> </div> <div class="dateFilter input-group"> <input id="resolvedToInput" class="form-control" placeholder="to RRRR-MM-DD"> <div id="resolvedTo"></div> <div class="input-group-btn"><button id="resolvedToToggle" class="btn btn-default glyphicon glyphicon-calendar"></button></div> </div> </div> <input type="button" value="Apply" class="btn btn-primary" onclick="submitFilter('{$myTicketsUrl}');" /> <input type="button" value="Cancel" class="btn btn-default" onclick="clearFilter('{$myTicketsUrl}');" /> </div> <script> {literal} WindowDatePicker.createLanguage('en', { DAYS_ABBR: ['', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat', 'Sun'], MONTHS: ['', 'January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December'], MONTHS_ABBR: ['', 'Jan', 'Feb', 'Mar', 'Apr', 'May', 'Jun', 'Jul', 'Aug', 'Sep', 'Oct', 'Nov', 'Dec'], AM_PM: ['AM', 'PM'], BUTTONS: ['Apply', 'Cancel'], INVALID_DATE: 'Invalid Date' }); {/literal} const createdFrom = new {literal}WindowDatePicker({{/literal} el: '#createdFrom', lang: 'en', toggleEl: '#createdFromToggle', inputEl: '#createdFromInput', value: '{$createdFrom}', type: 'DATE', dateType: 'YYYY-MM-DD', {literal}}); const createdTo = new WindowDatePicker({{/literal} el: '#createdTo', lang: 'en', toggleEl: '#createdToToggle', inputEl: '#createdToInput', value: '{$createdTo}', type: 'DATE', dateType: 'YYYY-MM-DD', {literal}});{/literal} const changedFrom = new {literal}WindowDatePicker({{/literal} el: '#changedFrom', lang: 'en', toggleEl: '#changedFromToggle', inputEl: '#changedFromInput', value: '{$changedFrom}', type: 'DATE', dateType: 'YYYY-MM-DD', {literal}}); const changedTo = new WindowDatePicker({{/literal} el: '#changedTo', lang: 'en', toggleEl: '#changedToToggle', inputEl: '#changedToInput', value: '{$changedTo}', type: 'DATE', dateType: 'YYYY-MM-DD', {literal}});{/literal} const resolvedFrom = new {literal}WindowDatePicker({{/literal} el: '#resolvedFrom', lang: 'en', toggleEl: '#resolvedFromToggle', inputEl: '#resolvedFromInput', value: '{$resolvedFrom}', type: 'DATE', dateType: 'YYYY-MM-DD', {literal}}); const resolvedTo = new WindowDatePicker({{/literal} el: '#resolvedTo', lang: 'en', toggleEl: '#resolvedToToggle', inputEl: '#resolvedToInput', value: '{$resolvedTo}', type: 'DATE', dateType: 'YYYY-MM-DD', {literal}});{/literal} </script> {/if} </div>
2. Switch to Custom CSS tab(Customer portal tab->Settings->Configuration->Design->Custom CSS). Add this CSS and save the changes. Feel free to adjust the CSS to match your exact design needs.
.select2-container {width: auto !important; display:block !important;} .select2-container > span {display:block !important;} .select2-container--default .select2-selection--multiple .select2-selection__choice__remove {color: inherit !important; font-size: 14px; line-height: 15px; vertical-align: bottom;} .select2-container--default .select2-selection--multiple .select2-selection__choice__remove:hover {opacity:0.5} .select2-container--default .select2-selection--multiple .select2-selection__choice {border-color:rgba(0,0,0,0.4) !important; float:none !important; font-size: 12px !important; text-overflow:ellipsis; overflow:hidden;} .filter_label { color: #666; font-size: 12px; } .filter-body { margin-bottom: 10px; } #filterQuery { border-radius: 4px; border: 1px solid #aaa; padding: 12px 8px; width: 100%; } .select2-results__options li[aria-selected="true"] {display:none;} .select2-results__option { border: 3px solid #fff; border-radius: 7px; font-size: 12px; line-height: 12px; } .select2-results__option:hover { opacity:0.8; } .dateFilter { margin-bottom:3px; } .dateFilter .input-group-btn:last-child > .btn, .dateFilter .input-group-btn:last-child > .btn-group { margin-top:-2px; } .dateFilter input { width: 48%; font-size: 13px; padding: 9px 5px; margin: 0; display: inline-block; } .dateFilter .form-control { box-shadow:none; } .dateFilter button { margin: 0; display: inline-block; } .btn {height:auto;}
3. Switch to Tracking codes tab(Customer portal tab->Settings->Configuration->Tracking codes). We will add some necessary scripts and functions here.
a) Add this code into the
<link href="https://www.cssscript.com/demo/window-date-time-picker/dist/css/window-date-picker.css" rel="stylesheet" type="text/css"> <link href="https://cdnjs.cloudflare.com/ajax/libs/select2/4.0.10/css/select2.min.css" rel="stylesheet" /> <script src="https://nostalgic-fermat-6932a4.netlify.com/window-date-picker.js"></script>
b) Add this code into the
<script src="https://nostalgic-fermat-6932a4.netlify.com/select2.js"></script> <script type="text/javascript"> $(document).ready(function() { $('.tags-select').select2(); }); $(document).ready(function() { $('.status-select').select2(); }); function clearFilter(url) { window.location.href = url; } function submitFilter(url) { filterQuery = []; if ($('.tags-select').val() != []) { filterQuery.push("t=" + $('.tags-select').val().join()); } if ($('.status-select').val() != "") { filterQuery.push("s=" + $('.status-select').val()); } if ($('#createdFromInput').val() != "") { filterQuery.push("created_from=" + $('#createdFromInput').val()); } if ($('#createdToInput').val() != "") { filterQuery.push("created_to=" + $('#createdToInput').val()); } if ($('#changedFromInput').val() != "") { filterQuery.push("changed_from=" + $('#changedFromInput').val()); } if ($('#changedToInput').val() != "") { filterQuery.push("changed_to=" + $('#changedToInput').val()); } if ($('#resolvedFromInput').val() != "") { filterQuery.push("resolved_from=" + $('#resolvedFromInput').val()); } if ($('#resolvedToInput').val() != "") { filterQuery.push("resolved_to=" + $('#resolvedToInput').val()); } if ($('#filterQuery').val() != "") { filterQuery.push("q=" + $('#filterQuery').val()); } window.location.href = url + "?" + filterQuery.join("&"); } </script>