Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 1 | frappe.pages["leaderboard"].on_page_load = function (wrapper) { |
| 2 | frappe.leaderboard = new frappe.Leaderboard(wrapper); |
| 3 | } |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 4 | |
| 5 | frappe.Leaderboard = Class.extend({ |
| 6 | |
| 7 | init: function (parent) { |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 8 | frappe.ui.make_app_page({ |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 9 | parent: parent, |
| 10 | title: "Leaderboard", |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 11 | single_column: false |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 12 | }); |
| 13 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 14 | this.parent = parent; |
| 15 | this.page = this.parent.page; |
| 16 | this.page.sidebar.html(`<ul class="module-sidebar-nav overlay-sidebar nav nav-pills nav-stacked"></ul>`); |
| 17 | this.$sidebar_list = this.page.sidebar.find('ul'); |
| 18 | |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 19 | // const list of doctypes |
vishdha | 09acb77 | 2018-02-20 12:44:11 +0530 | [diff] [blame] | 20 | this.doctypes = ["Customer", "Item", "Supplier", "Sales Partner","Sales Person"]; |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 21 | this.timespans = ["Week", "Month", "Quarter", "Year"]; |
vishdha | 09acb77 | 2018-02-20 12:44:11 +0530 | [diff] [blame] | 22 | this.desc_fields = ["total_sales_amount", "total_request","total_purchase_amount","commission_rate"]; |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 23 | this.filters = { |
vishdha | 09acb77 | 2018-02-20 12:44:11 +0530 | [diff] [blame] | 24 | "Customer": ["total_item_purchased_qty", "total_sales_amount","receivable_amount_outstanding_amount"], |
| 25 | "Item": ["total_purchase_amount", "total_purchased_qty", "total_sales_amount", "total_sold_qty","available_stock_qty"], |
| 26 | "Supplier": ["total_item_sold_qty", "total_purchase_amount","payable_amount_outstanding_amount"], |
| 27 | "Sales Partner": ["commission_rate", "target_qty", "target_amount", "total_sales_amount"], |
| 28 | "Sales Person": ["target_qty", "target_amount", "total_sales_amount"], |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 29 | }; |
| 30 | |
| 31 | // for saving current selected filters |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 32 | // TODO: revert to 0 index for doctype and timespan, and remove preset down |
| 33 | const _initial_doctype = this.doctypes[0]; |
| 34 | const _initial_timespan = this.timespans[0]; |
| 35 | const _initial_filter = this.filters[_initial_doctype]; |
| 36 | |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 37 | this.options = { |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 38 | selected_doctype: _initial_doctype, |
| 39 | selected_filter: _initial_filter, |
| 40 | selected_filter_item: _initial_filter[0], |
| 41 | selected_timespan: _initial_timespan, |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 42 | }; |
| 43 | |
| 44 | this.message = null; |
| 45 | this.make(); |
| 46 | }, |
| 47 | |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 48 | make: function () { |
| 49 | var me = this; |
| 50 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 51 | var $container = $(`<div class="leaderboard page-main-content"> |
| 52 | <div class="leaderboard-graph"></div> |
| 53 | <div class="leaderboard-list"></div> |
| 54 | </div>`).appendTo(this.page.main); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 55 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 56 | this.$graph_area = $container.find('.leaderboard-graph'); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 57 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 58 | this.doctypes.map(doctype => { |
| 59 | this.get_sidebar_item(doctype).appendTo(this.$sidebar_list); |
| 60 | }); |
| 61 | |
vishdha | d4491d3 | 2018-02-21 09:33:35 +0530 | [diff] [blame] | 62 | this.company_select = this.page.add_field({ |
| 63 | fieldname: 'company', |
| 64 | label: __('Company'), |
| 65 | fieldtype:'Link', |
| 66 | options:'Company', |
| 67 | default:frappe.defaults.get_default('company'), |
vishdha | 9a64d43 | 2018-02-21 11:26:58 +0530 | [diff] [blame^] | 68 | change: function() { |
vishdha | d4491d3 | 2018-02-21 09:33:35 +0530 | [diff] [blame] | 69 | me.options.selected_company = this.value; |
| 70 | me.make_request($container); |
| 71 | } |
| 72 | |
| 73 | }); |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 74 | this.timespan_select = this.page.add_select(__("Timespan"), |
| 75 | this.timespans.map(d => { |
| 76 | return {"label": __(d), value: d } |
| 77 | }) |
| 78 | ); |
| 79 | |
vishdha | d4491d3 | 2018-02-21 09:33:35 +0530 | [diff] [blame] | 80 | |
| 81 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 82 | // this.timespan_select.val(this.timespans[1]); |
| 83 | |
| 84 | this.type_select = this.page.add_select(__("Type"), |
| 85 | me.options.selected_filter.map(d => { |
| 86 | return {"label": __(frappe.model.unscrub(d)), value: d } |
| 87 | }) |
| 88 | ); |
| 89 | |
| 90 | this.$sidebar_list.on('click', 'li', function(e) { |
| 91 | let $li = $(this); |
| 92 | let doctype = $li.find('span').html(); |
| 93 | |
vishdha | 9a64d43 | 2018-02-21 11:26:58 +0530 | [diff] [blame^] | 94 | me.options.selected_company = frappe.defaults.get_default('company'); |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 95 | me.options.selected_doctype = doctype; |
| 96 | me.options.selected_filter = me.filters[doctype]; |
| 97 | me.options.selected_filter_item = me.filters[doctype][0]; |
| 98 | |
| 99 | me.type_select.empty().add_options( |
| 100 | me.options.selected_filter.map(d => { |
| 101 | return {"label": __(frappe.model.unscrub(d)), value: d } |
| 102 | }) |
| 103 | ); |
| 104 | |
| 105 | me.$sidebar_list.find('li').removeClass('active'); |
| 106 | $li.addClass('active'); |
| 107 | |
| 108 | me.make_request($container); |
| 109 | }); |
| 110 | |
| 111 | this.timespan_select.on("change", function() { |
| 112 | me.options.selected_timespan = this.value; |
| 113 | me.make_request($container); |
| 114 | }); |
| 115 | |
| 116 | this.type_select.on("change", function() { |
| 117 | me.options.selected_filter_item = this.value |
| 118 | me.make_request($container); |
| 119 | }); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 120 | |
| 121 | // now get leaderboard |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 122 | this.$sidebar_list.find('li:first').trigger('click'); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 123 | }, |
| 124 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 125 | make_request: function ($container) { |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 126 | var me = this; |
| 127 | |
| 128 | frappe.model.with_doctype(me.options.selected_doctype, function () { |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 129 | me.get_leaderboard(me.get_leaderboard_data, $container); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 130 | }); |
| 131 | }, |
| 132 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 133 | get_leaderboard: function (notify, $container, start=0) { |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 134 | var me = this; |
| 135 | |
| 136 | frappe.call({ |
| 137 | method: "erpnext.utilities.page.leaderboard.leaderboard.get_leaderboard", |
| 138 | args: { |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 139 | doctype: me.options.selected_doctype, |
| 140 | timespan: me.options.selected_timespan, |
vishdha | d4491d3 | 2018-02-21 09:33:35 +0530 | [diff] [blame] | 141 | company: me.options.selected_company, |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 142 | field: me.options.selected_filter_item, |
| 143 | start: start |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 144 | }, |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 145 | callback: function (r) { |
| 146 | let results = r.message || []; |
| 147 | |
| 148 | let graph_items = results.slice(0, 10); |
| 149 | |
| 150 | me.$graph_area.show().empty(); |
| 151 | let args = { |
Prateeksha Singh | 04c4ce3 | 2017-12-20 10:51:25 +0530 | [diff] [blame] | 152 | parent: '.leaderboard-graph', |
| 153 | data: { |
| 154 | datasets: [ |
| 155 | { |
| 156 | values: graph_items.map(d=>d.value) |
| 157 | } |
| 158 | ], |
| 159 | labels: graph_items.map(d=>d.name) |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 160 | }, |
Prateeksha Singh | 04c4ce3 | 2017-12-20 10:51:25 +0530 | [diff] [blame] | 161 | colors: ['light-green'], |
| 162 | format_tooltip_x: d=>d[me.options.selected_filter_item], |
| 163 | type: 'bar', |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 164 | height: 140 |
| 165 | }; |
Prateeksha Singh | 04c4ce3 | 2017-12-20 10:51:25 +0530 | [diff] [blame] | 166 | new Chart(args); |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 167 | |
| 168 | notify(me, r, $container); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 169 | } |
| 170 | }); |
| 171 | }, |
| 172 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 173 | get_leaderboard_data: function (me, res, $container) { |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 174 | if (res && res.message) { |
| 175 | me.message = null; |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 176 | $container.find(".leaderboard-list").html(me.render_list_view(res.message)); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 177 | } else { |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 178 | me.$graph_area.hide(); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 179 | me.message = "No items found."; |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 180 | $container.find(".leaderboard-list").html(me.render_list_view()); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 181 | } |
| 182 | }, |
| 183 | |
| 184 | render_list_view: function (items = []) { |
| 185 | var me = this; |
| 186 | |
| 187 | var html = |
| 188 | `${me.render_message()} |
| 189 | <div class="result" style="${me.message ? "display:none;" : ""}"> |
| 190 | ${me.render_result(items)} |
| 191 | </div>`; |
| 192 | |
| 193 | return $(html); |
| 194 | }, |
| 195 | |
| 196 | render_result: function (items) { |
| 197 | var me = this; |
| 198 | |
| 199 | var html = |
| 200 | `${me.render_list_header()} |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 201 | ${me.render_list_result(items)}`; |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 202 | |
| 203 | return html; |
| 204 | }, |
| 205 | |
| 206 | render_list_header: function () { |
| 207 | var me = this; |
| 208 | const _selected_filter = me.options.selected_filter |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 209 | .map(i => frappe.model.unscrub(i)); |
| 210 | const fields = ['name', me.options.selected_filter_item]; |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 211 | |
| 212 | const html = |
| 213 | `<div class="list-headers"> |
| 214 | <div class="list-item list-item--head" data-list-renderer="${"List"}"> |
| 215 | ${ |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 216 | fields.map(filter => { |
| 217 | const col = frappe.model.unscrub(filter); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 218 | return ( |
| 219 | `<div class="leaderboard-item list-item_content ellipsis text-muted list-item__content--flex-2 |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 220 | header-btn-base |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 221 | ${(col && _selected_filter.indexOf(col) !== -1) ? "text-right" : ""}"> |
| 222 | <span class="list-col-title ellipsis"> |
| 223 | ${col} |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 224 | </span> |
| 225 | </div>`); |
| 226 | }).join("") |
| 227 | } |
| 228 | </div> |
| 229 | </div>`; |
| 230 | return html; |
| 231 | }, |
| 232 | |
| 233 | render_list_result: function (items) { |
| 234 | var me = this; |
| 235 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 236 | let _html = items.map((item, index) => { |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 237 | const $value = $(me.get_item_html(item)); |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 238 | |
| 239 | let item_class = ""; |
| 240 | if(index == 0) { |
| 241 | item_class = "first"; |
| 242 | } else if (index == 1) { |
| 243 | item_class = "second"; |
| 244 | } else if(index == 2) { |
| 245 | item_class = "third"; |
| 246 | } |
| 247 | const $item_container = $(`<div class="list-item-container ${item_class}">`).append($value); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 248 | return $item_container[0].outerHTML; |
| 249 | }).join(""); |
| 250 | |
| 251 | let html = |
| 252 | `<div class="result-list"> |
| 253 | <div class="list-items"> |
| 254 | ${_html} |
| 255 | </div> |
| 256 | </div>`; |
| 257 | |
| 258 | return html; |
| 259 | }, |
| 260 | |
| 261 | render_message: function () { |
| 262 | var me = this; |
| 263 | |
| 264 | let html = |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 265 | `<div class="no-result text-center" style="${me.message ? "" : "display:none;"}"> |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 266 | <div class="msg-box no-border"> |
| 267 | <p>No Item found</p> |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 268 | </div> |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 269 | </div>`; |
| 270 | |
| 271 | return html; |
| 272 | }, |
| 273 | |
| 274 | get_item_html: function (item) { |
| 275 | var me = this; |
vishdha | 9a64d43 | 2018-02-21 11:26:58 +0530 | [diff] [blame^] | 276 | const company = frappe.defaults.get_default('Company'); |
| 277 | const currency = frappe.get_doc(":Company", company).default_currency; |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 278 | const _selected_filter = me.options.selected_filter |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 279 | .map(i => frappe.model.unscrub(i)); |
vishdha | d4491d3 | 2018-02-21 09:33:35 +0530 | [diff] [blame] | 280 | const fields = ['name','value']; |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 281 | |
| 282 | const html = |
| 283 | `<div class="list-item"> |
| 284 | ${ |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 285 | fields.map(filter => { |
| 286 | const col = frappe.model.unscrub(filter); |
| 287 | let val = item[filter]; |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 288 | if (col === "Modified") { |
| 289 | val = comment_when(val); |
| 290 | } |
| 291 | return ( |
| 292 | `<div class="list-item_content ellipsis list-item__content--flex-2 |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 293 | ${(col !== "Name" && col !== "Modified") ? "hidden-xs" : ""} |
vishdha | 09acb77 | 2018-02-20 12:44:11 +0530 | [diff] [blame] | 294 | ${(filter == "value") ? "text-right" : ""}"> |
vishdha | d4491d3 | 2018-02-21 09:33:35 +0530 | [diff] [blame] | 295 | ${ col === "Name" ? `<a class="grey list-id ellipsis" href="#Form/${me.options.selected_doctype}/${item["name"]}"> ${val} </a>` : `<span class="text-muted ellipsis"> ${format_currency(val, currency)}</span>` |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 296 | } |
| 297 | </div>`); |
| 298 | }).join("") |
| 299 | } |
| 300 | </div>`; |
| 301 | |
| 302 | return html; |
| 303 | }, |
| 304 | |
Prateeksha Singh | 9b4f3cf | 2017-09-18 16:41:04 +0530 | [diff] [blame] | 305 | get_sidebar_item: function(item) { |
| 306 | return $(`<li class="strong module-sidebar-item"> |
| 307 | <a class="module-link"> |
| 308 | <span>${ item }</span></a> |
| 309 | </li>`); |
Ayush Shukla | a111f78 | 2017-06-20 13:04:45 +0530 | [diff] [blame] | 310 | } |
| 311 | }); |