Vn.Shelves = new Class ({ Extends: Vn.Form ,activate: function () { this.$('date').value = new Date (); } ,onConfigChange: function () { var c = this.$('config'); this.$('warehouse').value = c.get ('warehouse_id'); this.$('shelf').value = c.get ('shelf_id'); this.$('reign').value = c.get ('reino_id'); this.$('family').value = c.get ('family_id'); this.$('filter').value = c.get ('name_prefix'); this.$('max-amount').value = c.get ('max_amount'); this.$('show-packing').value = c.get ('show_packing'); this.$('stack').value = c.get ('stack'); this.$('report-title').value = c.get ('name'); } ,onPreviewClick: function () { var batch = new Sql.Batch (); batch.addParams ({ 'shelf': this.$('shelf'), 'wh': this.$('warehouse'), 'date': this.$('date'), 'family': this.$('family'), 'filter': this.$('filter') }); var report = new Vn.ShelvesReport ({conn: this.conn}); report.setParams ( this.$('report-title').value, this.$('max-amount').value, this.$('show-packing').value, this.$('stack').value, batch ); report.open (); } }); Vn.ShelvesReport = new Class ({ Extends: Vn.Report ,nItem: -1 ,nColors: 5 ,setParams: function (title, maxAmount, showPacking, stack, batch) { this.title = title; this.maxAmount = maxAmount; this.batch = batch; this.showPacking = showPacking; this.stack = stack; } ,open: function () { var query = 'SELECT id, name, width, height, depth, max_height, tray_height, '+ 'first_tray_elevation, tray_density, vspacing, hspacing '+ 'FROM shelf WHERE id = #shelf; '+ 'CALL item_organizer (#wh, #date, #family, #filter)'; this.conn.execQuery (query, this.onQueryExec.bind (this), this.batch); } ,onQueryExec: function (resultSet) { // Fetch query data var res = resultSet.fetchResult (); res.next (); var maxWidth = 170; var maxHeight = 200; var scale = maxWidth / res.get ('width'); if (res.get ('max_height') * scale > maxHeight) scale = maxHeight / res.get ('max_height'); var shelf = this.shelf = { width: res.get ('width') * scale ,height: res.get ('height') * scale ,depth: res.get ('depth') * scale ,maxHeight: res.get ('max_height') * scale ,trayHeight: res.get ('tray_height') * scale ,firstTrayElevation: res.get ('first_tray_elevation') * scale ,trayDensity: res.get ('tray_density') * scale ,vspacing: res.get ('vspacing') * scale ,hspacing: res.get ('hspacing') * scale }; var items = []; var remainings = []; var res = resultSet.fetchResult (); if (res.data.length == 0) { Htk.Toast.showError (_('No items found, check that all fields are correct')); return; } var boxScale = scale * 10; while (res.next ()) if (!this.maxAmount || res.get ('etiquetas') <= this.maxAmount) { items.push ({ id: res.get ('Id_Article') ,name: res.get ('Article') ,packing: res.get ('packing') ,amount: res.get ('etiquetas') ,boxHeight: res.get ('z') * boxScale ,boxWidth: res.get ('x') * boxScale ,boxDepth: res.get ('y') * boxScale }); } else { remainings.push ({ id: res.get ('Id_Article') ,name: res.get ('Article') ,packing: res.get ('packing') ,amount: res.get ('etiquetas') }); } // Intializes the allocator alloc = new Vn.Allocator (); alloc.items = items; alloc.shelfFunc = this.drawShelf.bind (this); alloc.boxFunc = this.drawBox.bind (this); alloc.stack = this.stack; alloc.nTrays = Math.ceil ( (shelf.height - shelf.firstTrayElevation) / (shelf.trayHeight + shelf.trayDensity) ); alloc.width = shelf.width - shelf.hspacing * 2; alloc.depth = shelf.depth; alloc.trayHeight = shelf.trayHeight - shelf.vspacing; alloc.topTrayHeight = shelf.maxHeight - shelf.vspacing - shelf.firstTrayElevation - (alloc.nTrays - 1) * shelf.trayHeight; // Opens the report if (!this.createWindow ('shelves')) return; // Remaining amount if (remainings.length > 0) { var sheet = this.doc.createElement ('div'); sheet.className = 'sheet'; this.doc.body.appendChild (sheet); var title = this.doc.createElement ('h1'); title.className = 'title'; title.appendChild (this.doc.createTextNode (this.title)); sheet.appendChild (title); var subtitle = this.doc.createElement ('h2'); subtitle.className = 'subtitle'; subtitle.appendChild (this.doc.createTextNode (_('Pallets'))); sheet.appendChild (subtitle); var ul = this.doc.createElement ('ul'); sheet.appendChild (ul); for (var i = 0; i < remainings.length; i++) { var li = this.doc.createElement ('li'); ul.appendChild (li); var span = this.doc.createElement ('span'); span.className = 'item-id'; span.appendChild (this.doc.createTextNode (remainings[i].id.toLocaleString ())); li.appendChild (span); var span = this.doc.createElement ('span'); span.className = 'item'; span.appendChild (this.doc.createTextNode (remainings[i].name)); li.appendChild (span); if (this.showPacking) span.appendChild (this.doc.createTextNode (' '+ remainings[i].packing)); var span = this.doc.createElement ('span'); span.className = 'amount'; span.appendChild (this.doc.createTextNode (remainings[i].amount)); li.appendChild (span); } } // Draws the shelves alloc.run (); this.drawShelfEnding (); } ,drawShelf: function (allocator, item) { var shelf = this.shelf; var sheet = this.doc.createElement ('div'); sheet.className = 'sheet'; this.doc.body.appendChild (sheet); // Draws the title var pageNumber = this.doc.createElement ('h1'); pageNumber.className = 'page-number'; pageNumber.appendChild (this.doc.createTextNode (allocator.currentShelf + 1)); sheet.appendChild (pageNumber); var title = this.doc.createElement ('h1'); title.className = 'title'; title.appendChild (this.doc.createTextNode (this.title)); sheet.appendChild (title); var subtitle = this.doc.createElement ('h2'); subtitle.className = 'subtitle'; subtitle.appendChild (this.doc.createTextNode (item.id.toLocaleString ())); sheet.appendChild (subtitle); this.drawShelfEnding (); this.lastSubtitle = subtitle; // Draws the shelf var shelfDiv = this.shelfDiv = this.doc.createElement ('div'); shelfDiv.className = 'shelf'; shelfDiv.style.width = this.mm (shelf.width); shelfDiv.style.height = this.mm (shelf.maxHeight); sheet.appendChild (shelfDiv); // Draws trays var lastTrayY = shelf.firstTrayElevation; if (shelf.trayHeight > 0) while (lastTrayY + shelf.trayDensity < shelf.height) { var tray = this.doc.createElement ('div'); tray.className = 'tray'; tray.style.width = this.mm (shelf.width); tray.style.height = this.mm (shelf.trayDensity); tray.style.bottom = this.mm (lastTrayY); shelfDiv.appendChild (tray); lastTrayY += shelf.trayHeight + shelf.trayDensity; } } ,drawShelfEnding: function () { if (this.lastSubtitle) this.lastSubtitle.appendChild ( this.doc.createTextNode (' - '+ this.lastItem.id.toLocaleString ())); } ,mm: function (size) { return size.toFixed (2) +'mm'; } ,drawBox: function (allocator, item, amount) { if (item.boxWidth == 0 || item.boxHeight == 0) return; var shelf = this.shelf; var x = allocator.trayX + shelf.hspacing; var y = allocator.trayY + shelf.firstTrayElevation + shelf.trayDensity + allocator.currentTray * (shelf.trayHeight + shelf.trayDensity); var box = this.doc.createElement ('div'); box.className = 'box'; this.shelfDiv.appendChild (box); box.style.left = this.mm (x); box.style.bottom = this.mm (y); box.style.width = this.mm (item.boxWidth); box.style.height = this.mm (item.boxHeight); if (amount == 0) this.nItem++; var nColor = this.nItem % this.nColors; Vn.Node.addClass (box, 'color'+ nColor); if (amount == 0 || allocator.firstShelfBox) { var fontSize = item.boxWidth / 5.2; if (fontSize > item.boxHeight - 1) fontSize = item.boxHeight - 1; var boxLabel = this.doc.createElement ('div'); boxLabel.className = 'box-label'; boxLabel.style.fontSize = this.mm (fontSize); boxLabel.appendChild (this.doc.createTextNode (item.id.toLocaleString ())); box.appendChild (boxLabel); } this.lastItem = item; } }); Vn.Allocator = new Class ({ addShelf: function (item) { this.currentShelf++; this.firstShelfBox = true; if (this.shelfFunc) this.shelfFunc (this, item); } ,addTray: function (item) { if (this.currentTray <= 0) { this.addShelf (item); this.currentTray = this.nTrays - 1; } else this.currentTray--; this.trayX = 0; } ,addColumn: function (item) { if (this.trayX + this.columnWidth + item.boxWidth > this.width || this.currentTray == -1) this.addTray (item); else this.trayX += this.columnWidth; this.trayY = 0; this.columnWidth = item.boxWidth; this.lastBoxWidth = item.boxWidth; } ,addBox: function (item, amount) { var trayHeight = this.trayHeight; if (this.currentTray == this.nTrays - 1) trayHeight = this.topTrayHeight; if (this.trayY + item.boxHeight > trayHeight || item.boxWidth > this.lastBoxWidth || (!this.stack && amount == 0)) this.addColumn (item); if (this.boxFunc) this.boxFunc (this, item, amount); this.trayY += item.boxHeight; if (item.boxWidth < this.lastBoxWidth) this.lastBoxWidth = item.boxWidth; } ,run: function () { this.firstShelfBox = false; this.currentShelf = -1; this.currentTray = -1; this.columnWidth = 0; this.lastBoxWidth = 0; this.trayX = 0; this.trayY = 0; this.remaining = false; for (var i = 0; i < this.items.length; i++) { var item = this.items[i]; var boxIncrement = Math.floor (this.depth / item.boxDepth); if (boxIncrement < 1) boxIncrement = 1; for (var amount = 0; amount < item.amount; amount += boxIncrement) { this.addBox (item, amount); this.firstShelfBox = false; } } return this.currentShelf + 1; } });