diff --git a/src/css/classes.scss b/src/css/classes.scss index f4f907e55..afc0e7112 100644 --- a/src/css/classes.scss +++ b/src/css/classes.scss @@ -18,9 +18,9 @@ All rights reserved. width: 100%; } -.error { background: $color-error; } +.error { background: $color-error !important; } -.error-new { background: $color-error-new; } +.error-new { background: $color-error-new !important; } .section { margin-top: 3em; diff --git a/src/css/templates/inventory.scss b/src/css/templates/inventory.scss index 14a67f973..d4f793117 100644 --- a/src/css/templates/inventory.scss +++ b/src/css/templates/inventory.scss @@ -53,20 +53,6 @@ All rights reserved. vertical-align: middle; } - td.quantity { - position: relative; - width: 2.4em; - - input { - position: absolute; top: 50%; height: $font-size-small; width: 100%; - @include transform(translateY(-50%)); - border-radius: 0.75em; - margin: 0 auto; - text-align: center; - max-width: 2.8em; - } - } - td.icon { width: 4.8em; padding: 0 1em; diff --git a/src/css/templates/stack.scss b/src/css/templates/stack.scss index 3b3f3d57f..348ba2ab6 100644 --- a/src/css/templates/stack.scss +++ b/src/css/templates/stack.scss @@ -12,15 +12,39 @@ All rights reserved. padding: 0.2em 0; } - td.quantity p { - border-radius: 0.75em; - background: $color-ice; - color: $color-background-panel; - font-size: $font-size-normal; - font-weight: bold; - text-align: center; - min-width: 3em; - padding: 0.1em 0.5em; + td.quantity { + position: relative; + width: 4em; + + input { + position: absolute; top: 50%; height: $font-size-small; width: 100%; + @include transform(translateY(-50%)); + + border-radius: 0.75em; + background: $color-ice; + color: $color-background-panel; + font-family: $font-family-normal; + font-size: $font-size-normal; + font-weight: bold; + text-align: center; + + &.editable { + &:focus { + background: $color-background-panel; + color: $color-text; + font-family: $font-family-input; + font-weight: normal; + outline: none; + } + + &:hover { + background: $color-background-panel; + color: $color-text; + font-family: $font-family-input; + font-weight: normal; + } + } + } } td.icon { diff --git a/src/scripts/controllers/inventory_controller.coffee b/src/scripts/controllers/inventory_controller.coffee index 01ec6d37c..1f7e619ee 100644 --- a/src/scripts/controllers/inventory_controller.coffee +++ b/src/scripts/controllers/inventory_controller.coffee @@ -43,12 +43,15 @@ module.exports = class InventoryController extends BaseController # Event Methods ################################################################################ onAddButtonClicked: -> + if @$nameField.val().trim().length is 0 + @$nameField.focus() + return + item = @modPack.findItemByName @$nameField.val() return unless item? - @model.add item.slug, parseInt(@$quantityField.val()) + @model.add item.slug, 1 @$nameField.val '' - @$quantityField.val '1' @$scrollbox.scrollTop @$scrollbox.prop 'scrollHeight' @$nameField.autocomplete 'close' @@ -84,28 +87,6 @@ module.exports = class InventoryController extends BaseController if event.which is Key.Return @onAddButtonClicked() - onQuantityFieldBlur: -> - value = @$quantityField.val().replace /[^0-9]/g, '' - if value.length is 0 then value = '1' - value = Math.min value, InventoryController.MAX_QUANTITY - @$quantityField.val value - @onQuantityFieldChanged() - - onQuantityFieldChanged: -> - if not @$quantityField.val().match /^[0-9]*$/ - @$quantityField.addClass 'error', 0 - @$quantityField.addClass 'error-new', 0 - @$quantityField.removeClass 'error-new', Duration.slow - @$quantityField.focus() - return - - @$quantityField.removeClass 'error', Duration.normal - @$quantityField.removeClass 'error-new', Duration.normal - @_refreshButtonState() - - onQuantityFieldFocused: -> - @$quantityField.val '' - # BaseController Overrides ##################################################################### onDidRender: -> @@ -114,7 +95,6 @@ module.exports = class InventoryController extends BaseController @$icon = @$('.icon') @$editPanel = @$('.edit') @$nameField = @$('input[name="name"]') - @$quantityField = @$('input[name="quantity"]') @$scrollbox = @$('.scrollbox') @$table = @$('table') @$toolbar = @$('.toolbar') @@ -129,8 +109,6 @@ module.exports = class InventoryController extends BaseController @$icon.attr 'src', @icon @$title.html @title - if _.isEmpty(@$quantityField.val()) then @$quantityField.val '1' - @_refreshStacks() @_refreshNameAutocomplete() @_refreshButtonState() @@ -142,13 +120,10 @@ module.exports = class InventoryController extends BaseController events: -> return _.extend super, 'blur input[name="name"]': 'onNameFieldBlur' - 'blur input[name="quantity"]': 'onQuantityFieldBlur' 'click button[name="add"]': 'onAddButtonClicked' 'click button[name="clear"]': 'onClearButtonClicked' 'focus input[name="name"]': 'onNameFieldFocused' - 'focus input[name="quantity"]': 'onQuantityFieldFocused' 'input input[name="name"]': 'onNameFieldChanged' - 'input input[name="quantity"]': 'onQuantityFieldChanged' 'keyup input[name="name"]': 'onNameFieldKeyUp' # Private Methods ############################################################################## @@ -156,9 +131,9 @@ module.exports = class InventoryController extends BaseController _refreshButtonState: -> if @model.isEmpty then @$clearButton.attr('disabled', 'disabled') else @$clearButton.removeAttr('disabled') + noText = @$nameField.val().trim().length is 0 itemValid = @modPack.findItemByName(@$nameField.val())? - quantityValid = @$quantityField.val().match(InventoryController.ONLY_DIGITS) - disable = not (itemValid and quantityValid) + disable = not (itemValid or noText) if disable then @$addButton.attr('disabled', 'disabled') else @$addButton.removeAttr('disabled') _refreshNameAutocomplete: -> @@ -171,7 +146,6 @@ module.exports = class InventoryController extends BaseController minLength: 0 change: onChanged close: onChanged - minLength: 3 select: onSelected _refreshStacks: -> diff --git a/src/scripts/controllers/stack_controller.coffee b/src/scripts/controllers/stack_controller.coffee index c3e068f37..b29d637f5 100644 --- a/src/scripts/controllers/stack_controller.coffee +++ b/src/scripts/controllers/stack_controller.coffee @@ -6,13 +6,17 @@ All rights reserved. ### BaseController = require './base_controller' +{Duration} = require '../constants' {Event} = require '../constants' ImageLoader = require './image_loader' +{Key} = require '../constants' ######################################################################################################################## module.exports = class StackController extends BaseController + @MAX_QUANTITY = 9999 + constructor: (options={})-> if not options.imageLoader? then throw new Error 'options.imageLoader is required' if not options.model? then throw new Error 'options.model is required' @@ -32,6 +36,47 @@ module.exports = class StackController extends BaseController # Event Methods ################################################################################ + onQuantityFieldBlur: -> + quantityText = @$quantityField.val().trim() + if quantityText.length is 0 + quantity = @_priorValue + else if not quantityText.match /^[0-9]*$/ + quantity = 1 + else + quantity = parseInt quantityText, 10 + if _.isNaN quantity then quantity = 1 + + quantity = Math.min quantity, StackController.MAX_QUANTITY + quantity = Math.max 1, quantity + + if quantity? + @$quantityField.val "#{quantity}" + @$quantityField.removeClass 'error', Duration.snap + @$quantityField.removeClass 'error-new', Duration.snap + + @model.quantity = quantity + + onQuantityFieldChanged: -> + quantityText = @$quantityField.val().trim() + if not quantityText.match /^[0-9]*$/ + @$quantityField.addClass 'error', 0 + @$quantityField.addClass 'error-new', 0 + @$quantityField.removeClass 'error-new', Duration.fast + else + @$quantityField.removeClass 'error', Duration.snap + @$quantityField.removeClass 'error-new', Duration.snap + + onQuantityFieldFocused: -> + if @editable + @_priorValue = @model.quantity + @$quantityField.val '' + else + @$quantityField.blur() + + onQuantityKeyUp: (event)-> + if event.which is Key.Return + @$quantityField.blur() + onRemoveClicked: -> @onRemove @model @@ -41,7 +86,7 @@ module.exports = class StackController extends BaseController @$action = @$('.action') @$image = @$('.icon img') @$nameLink = @$('.name a') - @$quantityField = @$('.quantity p') + @$quantityField = @$('.quantity input') @$removeButton = @$('button.remove') super @@ -51,7 +96,14 @@ module.exports = class StackController extends BaseController @_imageLoader.load display.iconUrl, @$image @$nameLink.html display.itemName @$nameLink.attr 'href', display.itemUrl - @$quantityField.html @model.quantity + @$quantityField.val @model.quantity + + if @editable + @$quantityField.removeAttr 'readonly' + @$quantityField.addClass 'editable' + else + @$quantityField.attr 'readonly', 'readonly' + @$quantityField.removeClass 'editable' @$action.css display:(if @editable then 'table-cell' else 'none') @@ -61,5 +113,9 @@ module.exports = class StackController extends BaseController events: -> return _.extend super, - 'click button.remove': 'onRemoveClicked' - 'click .name a': 'routeLinkClick' + 'blur .quantity input': 'onQuantityFieldBlur' + 'click button.remove': 'onRemoveClicked' + 'click .name a': 'routeLinkClick' + 'focus .quantity input': 'onQuantityFieldFocused' + 'input .quantity input': 'onQuantityFieldChanged' + 'keyup .quantity input': 'onQuantityKeyUp' diff --git a/src/scripts/models/inventory.coffee b/src/scripts/models/inventory.coffee index e1ca99b56..40db95b05 100644 --- a/src/scripts/models/inventory.coffee +++ b/src/scripts/models/inventory.coffee @@ -115,6 +115,7 @@ module.exports = class Inventory extends BaseModel stack.quantity -= quantity if stack.quantity is 0 + @stopListening stack delete @_stacks[itemSlug] @_itemSlugs = _(@_itemSlugs).without itemSlug @@ -184,6 +185,7 @@ module.exports = class Inventory extends BaseModel stack = @_stacks[itemSlug] if not stack? stack = new Stack itemSlug:itemSlug, quantity:quantity + @listenTo stack, Event.change, => @trigger Event.change @_stacks[itemSlug] = stack @_itemSlugs.push itemSlug @_sort() diff --git a/src/templates/inventory.jade b/src/templates/inventory.jade index 255ea8729..9d5a132bd 100644 --- a/src/templates/inventory.jade +++ b/src/templates/inventory.jade @@ -13,8 +13,8 @@ .scrollbox table tr.edit - td.quantity: input(name="quantity") - td.icon: img(src="/images/unknown.png") + td.quantity + td.icon td.name(width="*"): input(name="name") td.action: button(name="add") add .toolbar diff --git a/src/templates/stack.jade b/src/templates/stack.jade index ef8399d1c..8909aaa0f 100644 --- a/src/templates/stack.jade +++ b/src/templates/stack.jade @@ -6,7 +6,7 @@ //- tr.view__stack - td.quantity: p + td.quantity: input td.icon: img(src='') td.name(width='*'): a td.action