partkeepr

fork of partkeepr
git clone https://git.e1e0.net/partkeepr.git
Log | Files | Refs | Submodules | README | LICENSE

commit 783aaed580fb3cfcbd7868de72f0ca5fb35050fa
parent 0b5393afb0809d70b7be64c6b413f9dde0173656
Author: Felicitus <felicitus@felicitus.org>
Date:   Wed, 29 Jun 2011 20:05:44 +0200

Added support for creating stock levels when creating party

Diffstat:
Mfrontend/js/Components/Part/Editor/PartEditor.js | 106+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++----------
Mfrontend/js/Components/Part/Editor/PartEditorWindow.js | 17++++++++++++++---
Mfrontend/js/Components/Part/PartDisplay.js | 7+++++--
Mfrontend/js/Components/Part/PartsManager.js | 8+++++---
Afrontend/js/Components/Widgets/UserComboBox.js | 27+++++++++++++++++++++++++++
Mfrontend/js/Models/Part.js | 4++++
Mfrontend/js/PartKeepr.js | 14++++++++++++++
Msrc/de/RaumZeitLabor/PartKeepr/Part/Part.php | 8++++++--
Msrc/de/RaumZeitLabor/PartKeepr/Part/PartService.php | 32+++++++++++++++++++++++++++++++-
9 files changed, 199 insertions(+), 24 deletions(-)

diff --git a/frontend/js/Components/Part/Editor/PartEditor.js b/frontend/js/Components/Part/Editor/PartEditor.js @@ -5,28 +5,49 @@ */ Ext.define('PartKeepr.PartEditor', { extend: 'PartKeepr.Editor', - border: false, + + // Assigned model model: 'PartKeepr.Part', + + // Layout stuff + border: false, layout: 'fit', bodyStyle: 'background:#DFE8F6;', + + /** + * Initializes the editor fields + */ initComponent: function () { + + // Defines the basic editor fields var basicEditorFields = [{ xtype: 'textfield', name: 'name', fieldLabel: i18n("Name"), allowBlank: false - },{ - xtype: 'numberfield', - fieldLabel: i18n('Minimum Stock'), - allowDecimals: false, - allowBlank: false, - name: 'minStockLevel', - value: 0, - minValue: 0 - },{ - xtype: 'PartUnitComboBox', - fieldLabel: i18n("Part Unit"), - name: 'partUnit' + }, + { + layout: 'column', + bodyStyle: 'background:#DFE8F6', + border: false, + items: [{ + xtype: 'numberfield', + fieldLabel: i18n('Minimum Stock'), + allowDecimals: false, + allowBlank: false, + labelWidth: 150, + name: 'minStockLevel', + value: 0, + columnWidth: 0.5, + minValue: 0 + },{ + xtype: 'PartUnitComboBox', + fieldLabel: i18n("Part Unit"), + columnWidth: 0.5, + margin: "0 0 0 5", + name: 'partUnit', + value: PartKeepr.getApplication().getDefaultPartUnit().get("id") + }] },{ xtype: 'CategoryComboBox', fieldLabel: i18n("Category"), @@ -50,31 +71,90 @@ Ext.define('PartKeepr.PartEditor', { name: 'status' },{ xtype: 'checkbox', + hideEmptyLabel: false, fieldLabel: '', boxLabel: i18n("Needs Review"), name: 'needsReview' }]; + // Creates the distributor grid this.partDistributorGrid = Ext.create("PartKeepr.PartDistributorGrid", { title: i18n("Distributors"), layout: 'fit' }); + // Creates the manufacturer grid this.partManufacturerGrid = Ext.create("PartKeepr.PartManufacturerGrid", { title: i18n("Manufacturers"), layout: 'fit' }); + // Creates the parameter grid this.partParameterGrid = Ext.create("PartKeepr.PartParameterGrid", { title: i18n("Parameters"), layout: 'fit' }); + // Creates the attachment grid this.partAttachmentGrid = Ext.create("PartKeepr.PartAttachmentGrid", { title: i18n("Attachments"), layout: 'fit' }); + // Adds stock level fields for new items + if (this.partMode && this.partMode == "create") { + this.initialStockLevel = Ext.create("Ext.form.field.Number", { + fieldLabel: i18n("Initial Stock Level"), + name: "initialStockLevel", + labelWidth: 150, + columnWidth: 0.5 + }); + + this.initialStockLevelUser = Ext.create("PartKeepr.UserComboBox", { + fieldLabel: i18n("Stock User"), + name: 'initialStockLevelUser', + columnWidth: 0.5, + margin: "0 0 0 5" + }); + + basicEditorFields.push({ + layout: 'column', + bodyStyle: 'background:#DFE8F6', + border: false, + items: [ + this.initialStockLevel, + this.initialStockLevelUser + ] + }); + + this.initialStockLevelPrice = Ext.create("Ext.form.field.Number", { + fieldLabel: i18n('Price'), + labelWidth: 150, + columnWidth: 0.5, + name: 'initialStockLevelPrice' + }); + + this.initialStockLevelPricePerItem = Ext.create("Ext.form.field.Checkbox", { + boxLabel: i18n("Per Item"), + columnWidth: 0.5, + margin: "0 0 0 5", + name: 'initialStockLevelPricePerItem' + }); + + basicEditorFields.push({ + layout: 'column', + bodyStyle: 'background:#DFE8F6', + border: false, + items: [ + this.initialStockLevelPrice, + this.initialStockLevelPricePerItem + ] + }); + + + } + + // Create a tab panel of all fields this.items = { xtype: 'tabpanel', border: false, diff --git a/frontend/js/Components/Part/Editor/PartEditorWindow.js b/frontend/js/Components/Part/Editor/PartEditorWindow.js @@ -16,19 +16,30 @@ Ext.define('PartKeepr.PartEditorWindow', { width: 600, minWidth: 600, minHeight: 300, - height: 450, + height: 380, + /* Default edit mode. If mode = "create", we show additional fields */ + partMode: 'edit', title: i18n("Add Part"), + /** + * Creates the part editor and put it into the window. + */ initComponent: function () { this.editor = Ext.create("PartKeepr.PartEditor", { - border: false + border: false, + partMode: this.partMode }); + + /* If the edit mode is "create", we need to enlarge the window a bit to fit the fields without scrolling */ + if (this.partMode && this.partMode == "create") { + this.height = 435; + } + this.items = [ this.editor ]; this.editor.on("editorClose", function () { this.close(); }, this); - /** * We need a delay, since if others are listening for "partSaved", the dialog plus the record could be destroyed * before any following listeners have a chance to receive the record, resulting in strange problems. diff --git a/frontend/js/Components/Part/PartDisplay.js b/frontend/js/Components/Part/PartDisplay.js @@ -111,8 +111,11 @@ Ext.define('PartKeepr.PartDisplay', { var values = {}; for (var i in r.data) { - console.log(r.data[i]); - values[i] = htmlentities(r.data[i]); + if (r.data[i] !== null) { + values[i] = htmlentities(r.data[i]); + } else { + values[i] = r.data[i]; + } } this.tpl.overwrite(this.getTargetEl(), values); diff --git a/frontend/js/Components/Part/PartsManager.js b/frontend/js/Components/Part/PartsManager.js @@ -109,13 +109,15 @@ Ext.define('PartKeepr.PartManager', { * Creates a new, empty part editor window */ onItemAdd: function () { - var j = Ext.create("PartKeepr.PartEditorWindow"); + var j = Ext.create("PartKeepr.PartEditorWindow", { + partMode: 'create' + }); var defaults = {}; - var defaultPartUnit = PartKeepr.getApplication().getPartUnitStore().find("default", true); + var defaultPartUnit = PartKeepr.getApplication().getPartUnitStore().findRecord("default", true); - defaults.partUnit = defaultPartUnit; + defaults.partUnit = defaultPartUnit.get("id"); defaults.category = this.grid.currentCategory; record = Ext.create("PartKeepr.Part", defaults); diff --git a/frontend/js/Components/Widgets/UserComboBox.js b/frontend/js/Components/Widgets/UserComboBox.js @@ -0,0 +1,27 @@ +Ext.define("PartKeepr.UserComboBox",{ + extend:"Ext.form.field.ComboBox", + alias: 'widget.UserComboBox', + displayField: 'username', + valueField: 'id', + autoSelect: true, + queryMode: 'local', + triggerAction: 'all', + forceSelection: true, + editable: false, + initComponent: function () { + this.store = PartKeepr.getApplication().getUserStore(); + + /* Workaround to remember the value when loading */ + this.store.on("beforeload", function () { + this._oldValue = this.getValue(); + }, this); + + /* Set the old value when load is complete */ + this.store.on("load", function () { + this.setValue(this._oldValue); + }, this); + + this.callParent(); + } +}); + diff --git a/frontend/js/Models/Part.js b/frontend/js/Models/Part.js @@ -16,6 +16,10 @@ Ext.define("PartKeepr.Part", { { name: 'needsReview', type: 'boolean'}, // Various things that don't belong to the part, but are transmitted anyways to make handling easier + { name: 'initialStockLevel', type: 'int'}, + { name: 'initialStockLevelUser', type: 'int'}, + { name: 'initialStockLevelPrice', type: 'float'}, + { name: 'initialStockLevelPricePerItem', type: 'boolean'}, { name: 'partUnitName', type: 'string'}, { name: 'footprintName', type: 'string'}, { name: 'storageLocationName',type: 'string'}, diff --git a/frontend/js/PartKeepr.js b/frontend/js/PartKeepr.js @@ -87,6 +87,13 @@ Ext.application({ pageSize: -1, autoLoad: false }); + + this.userStore = Ext.create("Ext.data.Store", + { + model: 'PartKeepr.User', + pageSize: -1, + autoLoad: false + }); }, setAdmin: function (admin) { this.admin = admin; @@ -112,6 +119,12 @@ Ext.application({ getDistributorStore: function () { return this.distributorStore; }, + getDefaultPartUnit: function () { + return this.partUnitStore.findRecord("default", true); + }, + getUserStore: function () { + return this.userStore; + }, getSiPrefixStore: function () { return this.siPrefixStore; }, @@ -153,6 +166,7 @@ Ext.application({ this.distributorStore.load(); this.partUnitStore.load(); this.unitStore.load(); + this.userStore.load(); Ext.defer(PartKeepr.getApplication().reloadStores, 100000, this); } }, diff --git a/src/de/RaumZeitLabor/PartKeepr/Part/Part.php b/src/de/RaumZeitLabor/PartKeepr/Part/Part.php @@ -427,8 +427,12 @@ class Part extends BaseEntity implements Serializable, Deserializable { $this->setComment($value); break; case "footprint": - $footprint = Footprint::loadById($value); - $this->setFootprint($footprint); + try { + $footprint = Footprint::loadById($value); + $this->setFootprint($footprint); + } catch (\Exception $e) { + // No footprint was found. Ignore it. + } break; case "minStockLevel": $this->setMinStockLevel($value); diff --git a/src/de/RaumZeitLabor/PartKeepr/Part/PartService.php b/src/de/RaumZeitLabor/PartKeepr/Part/PartService.php @@ -1,5 +1,7 @@ <?php namespace de\RaumZeitLabor\PartKeepr\Part; +use de\RaumZeitLabor\PartKeepr\User\User; + use de\RaumZeitLabor\PartKeepr\Service\RestfulService; declare(encoding = 'UTF-8'); @@ -48,9 +50,37 @@ class PartService extends Service implements RestfulService { $part->deserialize($this->getParameters()); PartKeepr::getEM()->persist($part); - PartKeepr::getEM()->flush(); + if ($this->getParameter("initialStockLevel") > 0) { + + try { + $user = User::loadById($this->getParameter("initialStockLevelUser")); + } catch (\Exception $e) { + $user = SessionManager::getCurrentSession()->getUser(); + } + + $stock = new StockEntry($part, intval($this->getParameter("initialStockLevel")), $user); + + if ($this->getParameter("initialStockLevelPricePerItem") == true) { + $price = floatval($this->getParameter("initialStockLevelPrice")); + } else { + $price = floatval($this->getParameter("initialStockLevelPrice")) / $this->getParameter("initialStockLevel"); + } + + if ($price != 0) { + $stock->setPrice($price); + } + + PartKeepr::getEM()->persist($stock); + + $part->updateStockLevel(); + + PartKeepr::getEM()->flush(); + + return array("data" => $part->serialize()); + } + return array("data" => $part->serialize()); }