Chrysostomos for scheduler
[myslice.git] / plugins / scheduler2 / static / js / scheduler2.js
diff --git a/plugins/scheduler2/static/js/scheduler2.js b/plugins/scheduler2/static/js/scheduler2.js
new file mode 100755 (executable)
index 0000000..dd0c8f8
--- /dev/null
@@ -0,0 +1,314 @@
+/*\r
+#\r
+# Copyright (c) 2013 NITLab, University of Thessaly, CERTH, Greece\r
+#\r
+# Permission is hereby granted, free of charge, to any person obtaining a copy\r
+# of this software and associated documentation files (the "Software"), to deal\r
+# in the Software without restriction, including without limitation the rights\r
+# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell\r
+# copies of the Software, and to permit persons to whom the Software is\r
+# furnished to do so, subject to the following conditions:\r
+#\r
+# The above copyright notice and this permission notice shall be included in\r
+# all copies or substantial portions of the Software.\r
+#\r
+# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\r
+# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\r
+# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE\r
+# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER\r
+# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,\r
+# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN\r
+# THE SOFTWARE.\r
+#\r
+#\r
+# This is a MySlice plugin for the NITOS Scheduler\r
+# Nitos Scheduler v1\r
+#\r
+*/\r
+\r
+/* some params */\r
+var init_start_visible_index = 10;\r
+var init_end_visible_index = 21;\r
+var rsvrTblNm = "scheduler-reservation-table";\r
+var SchedulerResources = [];\r
+var schdlr_totalColums = 0;\r
+var SetPerFun = null;\r
+var Sched2 = null;\r
+var Debug = true;\r
+var schdlr_PartsInOneHour = 6;\r
+\r
+(function ($) {\r
+    var Scheduler2 = Plugin.extend({\r
+\r
+        /** XXX to check\r
+         * @brief Plugin constructor\r
+         * @param options : an associative array of setting values\r
+         * @param element : \r
+         * @return : a jQuery collection of objects on which the plugin is\r
+         *     applied, which allows to maintain chainability of calls\r
+         */\r
+        init: function (options, element) {\r
+            // Call the parent constructor, see FAQ when forgotten\r
+            this._super(options, element);\r
+\r
+            schdlr_totalColums = $("#scheduler-reservation-table th").length;\r
+\r
+            //selection from table \r
+            $(window).keydown(function (evt) {\r
+                if (evt.which == 17) { // ctrl\r
+                    ctrlPressed = true;\r
+                }\r
+            }).keyup(function (evt) {\r
+                if (evt.which == 17) { // ctrl\r
+                    ctrlPressed = false;\r
+                }\r
+            });\r
+            $("#" + rsvrTblNm).on('mousedown', 'td', rangeMouseDown).on('mouseup', 'td', rangeMouseUp).on('mousemove', 'td', rangeMouseMove);\r
+\r
+            // Explain this will allow query events to be handled\r
+            // What happens when we don't define some events ?\r
+            // Some can be less efficient\r
+\r
+            if (Debug) console.time("Listening_to_queries");\r
+            /* Listening to queries */\r
+            this.listen_query(options.query_uuid, 'all_ev');\r
+            this.listen_query(options.query_all_resources_uuid, 'all_resources');\r
+            this.listen_query(options.query_lease_uuid, 'lease');\r
+            //this.listen_query(options.query_lease_uuid, 'lease');\r
+            if (Debug) console.timeEnd("Listening_to_queries");\r
+\r
+        },\r
+\r
+        /* PLUGIN EVENTS */\r
+        // on_show like in querytable\r
+\r
+\r
+        /* GUI EVENTS */\r
+\r
+        // a function to bind events here: click change\r
+        // how to raise manifold events\r
+\r
+\r
+        /* GUI MANIPULATION */\r
+\r
+        // We advise you to write function to change behaviour of the GUI\r
+        // Will use naming helpers to access content _inside_ the plugin\r
+        // always refer to these functions in the remaining of the code\r
+\r
+        show_hide_button: function () {\r
+            // this.id, this.el, this.cl, this.elts\r
+            // same output as a jquery selector with some guarantees\r
+        },\r
+\r
+        drawResources: function () {\r
+            \r
+            //if (Debug) this.debug('foo');\r
+            if (Debug) console.time("each:SchedulerResources");\r
+\r
+            //scheduler-reservation-table main table columns\r
+            totalColums = $("#scheduler-reservation-table thead tr th").length;\r
+            //var totalCell = [];\r
+            //for (var i = 0; i < totalColums; i++) { totalCell.push("<td></td>"); }\r
+            //var srt_body = [];\r
+            var totalCell = "";\r
+            for (var i = 0; i < totalColums; i++) totalCell +="<td></td>"; \r
+            var srt_body = "";\r
+\r
+            $.each(SchedulerResources, function (i, group) {\r
+                //var groupTR = $("#ShedulerNodes tbody").html('<tr><td class="no-image verticalIndex" rowspan="' + group.resources.length + '"><div class="verticalText">' + group.groupName + '</div></td><td id="schdlr_frstTD" class="info fixed"></td></tr>');\r
+                var groupTR = $("#ShedulerNodes tbody").html('<tr><td class="no-image verticalIndex" rowspan="' + 30 + '"><div class="verticalText">' + group.groupName + '</div></td><td id="schdlr_frstTD" class="info fixed"></td></tr>');\r
+                \r
+                $.each(group.resources.slice(0,30), function (i, resource) {\r
+                    if (i == 0) {\r
+                        //$("#ShedulerNodes tbody tr:first").append('<td class="info fixed">' + resource.hostname + '</td>');\r
+                        $(groupTR).find("#schdlr_frstTD").html(resource.hostname);\r
+                        //$(srt_body).html("<tr>" + totalCell + "</tr>");\r
+                    } else {\r
+                        $(groupTR).find("tr:last").after('<tr><td class="info fixed">' + resource.hostname + '</td></tr>');\r
+                        //$(srt_body).find("tr:last").after("<tr>" + totalCell + "</tr>");\r
+                    }\r
+                    srt_body += "<tr>" + totalCell + "</tr>";\r
+                    //srt_body.push('<tr>'); srt_body = srt_body.concat(totalCell.concat()); srt_body.push('/<tr>');\r
+                });\r
+            });\r
+\r
+            //$("#scheduler-reservation-table tbody").html(srt_body.join(""));\r
+            $("#scheduler-reservation-table tbody").html(srt_body);\r
+\r
+            if (Debug) console.timeEnd("each:SchedulerResources");\r
+            \r
+\r
+            $("#" + rsvrTblNm + " tbody tr").each(function (index) { $(this).attr("data-trindex", index); });\r
+\r
+        },\r
+\r
+        /* TEMPLATES */\r
+\r
+        // see in the html template\r
+        // How to load a template, use of mustache\r
+\r
+        /* QUERY HANDLERS */\r
+        loadWithDate: function () {\r
+            // only convention, not strictly enforced at the moment\r
+        },\r
+        // How to make sure the plugin is not desynchronized\r
+        // He should manifest its interest in filters, fields or records\r
+        // functions triggered only if the proper listen is done\r
+\r
+        /* all_ev QUERY HANDLERS Start */\r
+        on_all_ev_clear_records: function (data) {\r
+            //alert('all_ev clear_records');\r
+        },\r
+        on_all_ev_query_in_progress: function (data) {\r
+           // alert('all_ev query_in_progress');\r
+        },\r
+        on_all_ev_new_record: function (data) {\r
+            //alert('all_ev new_record');\r
+        },\r
+        on_all_ev_query_done: function (data) {\r
+            //alert('all_ev query_done');\r
+        },\r
+        //another plugin has modified something, that requires you to update your display. \r
+        on_all_ev_field_state_changed: function (data) {\r
+            //alert('all_ev query_done');\r
+        },\r
+        /* all_ev QUERY HANDLERS End */\r
+        /* all_resources QUERY HANDLERS Start */\r
+        on_all_resources_clear_records: function (data) {\r
+            //data is empty on load\r
+        },\r
+        on_all_resources_query_in_progress: function (data) {\r
+            //data is empty on load\r
+        },\r
+        on_all_resources_new_record: function (data) {\r
+            var tmpGroup = lookup(SchedulerResources, 'groupName', data.type);\r
+            if (tmpGroup == null) {\r
+                tmpGroup = { groupName: data.type, resources: [] };\r
+                SchedulerResources.push(tmpGroup);\r
+                //if (data.type != "node")  alert('not all node');\r
+            }\r
+            tmpGroup.resources.push(data);\r
+            //alert('new_record');\r
+        },\r
+        on_all_resources_query_done: function (data) {\r
+            this.drawResources();\r
+            //data is empty on load\r
+            /* GUI setup and event binding */\r
+            this._initUI();\r
+            this._SetPeriodInPage(init_start_visible_index, init_end_visible_index);\r
+            this.loadWithDate();\r
+        },\r
+        //another plugin has modified something, that requires you to update your display. \r
+        on_all_resources_field_state_changed: function (data) {\r
+            //alert('all_resources query_done');\r
+        },\r
+        /* all_resources QUERY HANDLERS End */\r
+        /* lease QUERY HANDLERS Start */\r
+        on_lease_clear_records: function (data) { alert('clear_records'); },\r
+        on_lease_query_in_progress: function (data) { alert('query_in_progress'); },\r
+        on_lease_new_record: function (data) { alert('new_record'); },\r
+        on_lease_query_done: function (data) { alert('query_done'); },\r
+        //another plugin has modified something, that requires you to update your display. \r
+        on_lease_field_state_changed: function (data) { alert('query_done'); },\r
+        /* lease QUERY HANDLERS End */\r
+\r
+\r
+        // no prefix\r
+\r
+        on_filter_added: function (filter) {\r
+\r
+        },\r
+\r
+        // ... be sure to list all events here\r
+\r
+        /* RECORD HANDLERS */\r
+        on_all_new_record: function (record) {\r
+            //\r
+            alert('on_all_new_record');\r
+        },\r
+\r
+        debug : function (log_txt) {\r
+            if (typeof window.console != 'undefined') {\r
+                console.debug(log_txt);\r
+            }\r
+        },\r
+\r
+        /* INTERNAL FUNCTIONS */\r
+        _initUI: function () {\r
+            if (Debug) console.time("_initUI");\r
+            //fix margins in tables\r
+            mtNodesTbl = $("#" + rsvrTblNm + " tr:first").outerHeight() + 6;\r
+            mtSchrollCon = $("#nodes").outerWidth();\r
+            $("#nodes").css("margin-top", mtNodesTbl);\r
+            $("#reservation-table-scroll-container").css("margin-left", mtSchrollCon);\r
+            SetPerFun = this._SetPeriodInPage;\r
+            //slider\r
+            $("#time-range").slider({\r
+                range: true,\r
+                min: 0,\r
+                max: 24,\r
+                step: 0.5,\r
+                values: [init_start_visible_index, init_end_visible_index],\r
+                slide: function (event, ui) {\r
+                    SetPerFun(ui.values[0], ui.values[1]);\r
+                }\r
+            });\r
+            $("#DateToRes").datepicker({\r
+                dateFormat: "yy-mm-dd",\r
+                minDate: 0,\r
+                numberOfMonths: 3\r
+            }).change(function () {\r
+                //Scheduler2.loadWithDate();\r
+            }).click(function () {\r
+                $("#ui-datepicker-div").css("z-index", 5);\r
+            });\r
+            //other stuff\r
+            fixOddEvenClasses();\r
+            $("#" + rsvrTblNm + " td:not([class])").addClass("free");\r
+            if (Debug) console.timeEnd("_initUI");\r
+        },\r
+        _SetPeriodInPage: function (start, end) {\r
+            if (Debug) console.time("_SetPeriodInPage");\r
+            ClearTableSelection();\r
+            $("#lbltime").html(GetTimeFromInt(start) + " - " + GetTimeFromInt(end));\r
+            \r
+            var start_visible_index = (start * schdlr_PartsInOneHour) + 1;\r
+            var end_visible_index = (end * schdlr_PartsInOneHour);\r
+\r
+            //hide - show\r
+            for (i = 0; i < start_visible_index; i++) {\r
+                $("#" + rsvrTblNm + " td:nth-child(" + i + "), #" + rsvrTblNm + " th:nth-child(" + i + ")").hide();\r
+            }\r
+            for (i = end_visible_index + 1; i <= schdlr_totalColums; i++) {\r
+                $("#" + rsvrTblNm + " td:nth-child(" + i + "), #" + rsvrTblNm + " th:nth-child(" + i + ")").hide();\r
+            }\r
+            /*$("#" + rsvrTblNm + " td:not([class*='info']), #" + rsvrTblNm + " th:not([class*='fixed'])").hide();*/\r
+            for (i = start_visible_index; i <= end_visible_index; i++) {\r
+                $("#" + rsvrTblNm + " td:nth-child(" + i + "), #" + rsvrTblNm + " th:nth-child(" + i + ")").show();\r
+            }\r
+\r
+            if ($("#" + rsvrTblNm + " th:visible:first").width() > 105) {\r
+                $("#" + rsvrTblNm + " th span").css("display", "inline")\r
+            } else {\r
+                $("#" + rsvrTblNm + " th span").css("display", "block");\r
+            }\r
+            mtNodesTbl = $("#" + rsvrTblNm + " tr:first").outerHeight() + 6;\r
+            $("#nodes").css("margin-top", mtNodesTbl);\r
+            //$("#scroll_container").width($("#Search").width() - $("#nodes").width());\r
+            //$("#nodes th").height($("#tblReservation th:visible:first").height() - 2);\r
+            if (Debug) console.timeEnd("_SetPeriodInPage");\r
+        }\r
+    });\r
+\r
+    //Sched2 = new Scheduler2();\r
+\r
+    /* Plugin registration */\r
+    $.plugin('Scheduler2', Scheduler2);\r
+\r
+    // TODO Here use cases for instanciating plugins in different ways like in the pastie.\r
+\r
+\r
+})(jQuery);\r
+\r
+\r
+\r