From 680872a3022df5169c87797373f1ff1f57112598 Mon Sep 17 00:00:00 2001 From: Colin McLeod Date: Tue, 30 Jun 2015 21:06:12 -0700 Subject: [PATCH] Retrofitting costs added to outfit page --- app/js/controllers/controller-outfit.js | 84 ++++++++++++++++++++-- app/less/outfit.less | 19 +++++ app/less/select.less | 11 +++ app/views/page-outfit.html | 92 ++++++++++++++++++++----- test/tests/test-controller-outfit.js | 50 ++++++++++++++ 5 files changed, 233 insertions(+), 23 deletions(-) create mode 100644 test/tests/test-controller-outfit.js diff --git a/app/js/controllers/controller-outfit.js b/app/js/controllers/controller-outfit.js index da571241..d23e9ef0 100755 --- a/app/js/controllers/controller-outfit.js +++ b/app/js/controllers/controller-outfit.js @@ -1,7 +1,8 @@ angular.module('app').controller('OutfitController', ['$window', '$rootScope', '$scope', '$state', '$stateParams', 'ShipsDB', 'Ship', 'Components', 'Serializer', 'Persist', 'calcTotalRange', 'calcSpeed', function($window, $rootScope, $scope, $state, $p, Ships, Ship, Components, Serializer, Persist, calcTotalRange, calcSpeed) { + var win = angular.element($window); // Angularized window object for event triggering var data = Ships[$p.shipId]; // Retrieve the basic ship properties, slots and defaults var ship = new Ship($p.shipId, data.properties, data.slots); // Create a new Ship instance - var win = angular.element($window); // Angularized window object for event triggering + var retrofitShip = new Ship($p.shipId, data.properties, data.slots); // Create a new Ship for retrofit comparison // Update the ship instance with the code (if provided) or the 'factory' defaults. if ($p.code) { @@ -11,8 +12,6 @@ angular.module('app').controller('OutfitController', ['$window', '$rootScope', ' ship.buildWith(data.defaults); // Populate with default components } - ship.applyDiscounts($rootScope.discounts.ship, $rootScope.discounts.components); - $scope.buildName = $p.bn; $rootScope.title = ship.name + ($scope.buildName ? ' - ' + $scope.buildName : ''); $scope.ship = ship; @@ -32,11 +31,27 @@ angular.module('app').controller('OutfitController', ['$window', '$rootScope', ' $scope.selectedSlot = null; $scope.savedCode = Persist.getBuild(ship.id, $scope.buildName); $scope.canSave = Persist.isEnabled(); + $scope.allBuilds = Persist.builds; $scope.fuel = 0; $scope.pwrDesc = false; $scope.pwrPredicate = 'type'; + $scope.retroDesc = false; + $scope.retroPredicate = 'netCost'; $scope.costDesc = true; $scope.costPredicate = 'c.cost'; + $scope.costTab = 'retrofit'; + + if ($scope.savedCode) { + Serializer.toShip(retrofitShip, $scope.savedCode); // Populate components from last save + $scope.retrofitBuild = $scope.buildName; + } else { + retrofitShip.buildWith(data.defaults); + $scope.retrofitBuild = null; + } + + ship.applyDiscounts($rootScope.discounts.ship, $rootScope.discounts.components); + retrofitShip.applyDiscounts($rootScope.discounts.ship, $rootScope.discounts.components); + updateRetrofitCosts(); $scope.jrSeries = { xMin: 0, @@ -189,6 +204,9 @@ angular.module('app').controller('OutfitController', ['$window', '$rootScope', ' if ($scope.code != $scope.savedCode) { Persist.saveBuild(ship.id, $scope.buildName, $scope.code); $scope.savedCode = $scope.code; + if ($scope.retrofitBuild === $scope.buildName) { + Serializer.toShip(retrofitShip, $scope.code); + } updateState($scope.code); } }; @@ -232,6 +250,11 @@ angular.module('app').controller('OutfitController', ['$window', '$rootScope', ' $scope.pwrPredicate = key; }; + $scope.sortRetrofit = function(key) { + $scope.retroDesc = $scope.retroPredicate == key ? !$scope.retroDesc : $scope.retroDesc; + $scope.retroPredicate = key; + }; + /** * Toggle the power on/off for the selected component * @param {object} item The component being toggled @@ -266,6 +289,15 @@ angular.module('app').controller('OutfitController', ['$window', '$rootScope', ' return ship.getSlotStatus(slot, true); }; + $scope.setRetrofitBase = function() { + if ($scope.retrofitBuild) { + Serializer.toShip(retrofitShip, Persist.getBuild(ship.id, $scope.retrofitBuild)); + } else { + retrofitShip.buildWith(data.defaults); + } + updateRetrofitCosts(); + }; + // Utilify functions function updateState(code) { @@ -274,17 +306,61 @@ angular.module('app').controller('OutfitController', ['$window', '$rootScope', ' $scope.speedSeries.xMax = $scope.trSeries.xMax = $scope.jrSeries.xMax = ship.cargoCapacity; $scope.jrSeries.yMax = ship.unladenRange; $scope.trSeries.yMax = ship.unladenTotalRange; + updateRetrofitCosts(); win.triggerHandler('pwrchange'); } + function updateRetrofitCosts() { + var costs = $scope.retrofitList = []; + var cName = $rootScope.cName; + var total = 0, i, l, item; + + if (ship.bulkheads.id != retrofitShip.bulkheads.id) { + item = { + buyClassRating: ship.bulkheads.c.class + ship.bulkheads.c.rating, + buyName: cName(ship.bulkheads), + sellClassRating: retrofitShip.bulkheads.c.class + retrofitShip.bulkheads.c.rating, + sellName: cName(retrofitShip.bulkheads), + netCost: ship.bulkheads.discountedCost - retrofitShip.bulkheads.discountedCost + }; + costs.push(item); + total += item.netCost; + } + + for (var g in { common: 1, internal: 1, hardpoints: 1 }) { + var retroSlotGroup = retrofitShip[g]; + var slotGroup = ship[g]; + for (i = 0, l = slotGroup.length; i < l; i++) { + if (slotGroup[i].id != retroSlotGroup[i].id) { + item = { netCost: 0 }; + if (slotGroup[i].id) { + item.buyName = cName(slotGroup[i]); + item.buyClassRating = slotGroup[i].c.class + slotGroup[i].c.rating; + item.netCost = slotGroup[i].discountedCost; + } + if (retroSlotGroup[i].id) { + item.sellName = cName(retroSlotGroup[i]); + item.sellClassRating = retroSlotGroup[i].c.class + retroSlotGroup[i].c.rating; + item.netCost -= retroSlotGroup[i].discountedCost; + } + costs.push(item); + total += item.netCost; + } + } + } + $scope.retrofitTotal = total; + } + // Hide any open menu/slot/etc if the background is clicked $scope.$on('close', function() { $scope.selectedSlot = null; }); - // Hide any open menu/slot/etc if the background is clicked + // Hide any open menu/slot/etc if the background is clicked $scope.$on('discountChange', function() { ship.applyDiscounts($rootScope.discounts.ship, $rootScope.discounts.components); + retrofitShip.applyDiscounts($rootScope.discounts.ship, $rootScope.discounts.components); + updateRetrofitCosts(); }); }]); diff --git a/app/less/outfit.less b/app/less/outfit.less index 86066253..cacebbdc 100755 --- a/app/less/outfit.less +++ b/app/less/outfit.less @@ -113,6 +113,25 @@ table.total { } } +.tabs { + width: 100%; + margin-bottom: 1px; + + &, th { + border-collapse: collapse; + color: @primary-disabled; + background-color: @primary-bg; + border: 1px solid @primary-disabled; + padding-top: 1px; + } + + .active { + color: @primary-bg; + background-color: @primary-disabled; + } + +} + .group { width: 25%; padding: 0.5em 0.2em; diff --git a/app/less/select.less b/app/less/select.less index 98e8c8de..50d150bd 100755 --- a/app/less/select.less +++ b/app/less/select.less @@ -1,3 +1,14 @@ +select { + .border-radius(0); + background: none; + color: @primary-disabled; + border: 1px solid @primary-disabled; + outline: none; + font-family: @fStandard; + font-size: 1em; + background-color: transparent; +} + .select { color: @primary-disabled; position: absolute; diff --git a/app/views/page-outfit.html b/app/views/page-outfit.html index 2bd73566..7f344b4e 100644 --- a/app/views/page-outfit.html +++ b/app/views/page-outfit.html @@ -239,28 +239,38 @@
- +
- - - + + + - - - - - - -
- Component -
- [Ship {{fRPct(1 - discounts.ship)}} off] - [Components {{fRPct(1 - discounts.components)}} off] -
-
Credits
Retrofit CostsCosts
{{item.c.class}}{{item.c.rating}}{{cName(item)}}{{fCrd(item.discountedCost)}} CR
- + +
+
+ + + + + + + + + + + + + +
+ Component +
+ [Ship {{fRPct(1 - discounts.ship)}} off] + [Components {{fRPct(1 - discounts.components)}} off] +
+
Credits
{{item.c.class}}{{item.c.rating}}{{cName(item)}}{{fCrd(item.discountedCost)}} CR
+ @@ -269,7 +279,51 @@ -
Total {{fCrd(ship.totalCost)}} CRInsurance {{fCrd(ship.totalCost * insurance.current.pct)}} CR
+ +
+ +
+ + + + + + + + + + + + + + + + + + + + +
SellBuy + Net Cost +
+ [{{fRPct(1 - discounts.components)}} off] +
+
No Retrofitting changes
{{item.sellClassRating}}{{item.sellName}}{{item.buyClassRating}}{{item.buyName}}{{ fCrd(item.netCost)}} CR
+ + + + + + + + + +
Cost{{fCrd(retrofitTotal)}} CR
Retrofitting from + +
+
diff --git a/test/tests/test-controller-outfit.js b/test/tests/test-controller-outfit.js new file mode 100644 index 00000000..a25ed9db --- /dev/null +++ b/test/tests/test-controller-outfit.js @@ -0,0 +1,50 @@ +describe("Outfit Controller", function() { + beforeEach(module('app')); + + var outfitController, scope; + + var eventStub = { + preventDefault: function(){ }, + stopPropagation: function(){ } + }; + + beforeEach(inject(function(_$rootScope_, $controller) { + $rootScope = _$rootScope_; + $rootScope.discounts = { ship: 1, components: 1}; + $stateParams = { shipId: 'anaconda'}; + scope = $rootScope.$new(); + outfitController = $controller('OutfitController', { $rootScope: $rootScope, $scope: scope, $stateParams: $stateParams }); + })); + + describe("Retrofitting Costs", function() { + + it("are empty by default", function() { + expect(scope.retrofitTotal).toEqual(0); + expect(scope.retrofitList.length).toEqual(0); + }); + + it("updates on bulkheads change", function() { + scope.select('b', scope.ship.bulkheads, eventStub, "1"); // Use Reinforced Alloy Bulkheads + expect(scope.retrofitTotal).toEqual(58787780); + expect(scope.retrofitList.length).toEqual(1); + scope.select('b', scope.ship.bulkheads, eventStub, "0"); // Use Reinforced Alloy Bulkheads + expect(scope.retrofitTotal).toEqual(0); + expect(scope.retrofitList.length).toEqual(0); + }); + + it("updates on component change", function() { + scope.select('h', scope.ship.hardpoints[0], eventStub, "0u"); // 3C/F Beam Laser + expect(scope.retrofitTotal).toEqual(1177600); + expect(scope.retrofitList.length).toEqual(1); + scope.select('h', scope.ship.hardpoints[6], eventStub, "empty"); // Remove default pulse laser + scope.select('h', scope.ship.hardpoints[7], eventStub, "empty"); // Remove default pulse laser + expect(scope.retrofitTotal).toEqual(1173200); + expect(scope.retrofitList.length).toEqual(3); + scope.select('i', scope.ship.internal[3], eventStub, "11"); // Use 6A Auto field maintenance unit + expect(scope.retrofitTotal).toEqual(16478701); + expect(scope.retrofitList.length).toEqual(4); + }); + + }); + +});