From 0c4c5b899b908336ea5d781876c8d0c73b2972a2 Mon Sep 17 00:00:00 2001 From: Dan Elbert Date: Wed, 12 Sep 2018 17:17:15 -0500 Subject: [PATCH] updates --- app/controllers/calculator_controller.rb | 21 +++++--- app/controllers/logs_controller.rb | 4 +- app/controllers/recipes_controller.rb | 2 +- app/javascript/components/AppRating.vue | 9 +++- app/javascript/components/RecipeEdit.vue | 4 -- app/javascript/components/TaskItemList.vue | 54 +++++++++---------- app/javascript/components/TheCalculator.vue | 12 ++--- app/javascript/components/TheTaskListList.vue | 14 +++-- app/javascript/lib/Api.js | 3 +- app/javascript/styles/_transitions.scss | 9 ++-- app/models/food.rb | 10 +--- app/models/ingredient.rb | 41 ++++++++++++++ app/models/nutrition_data.rb | 2 +- app/models/recipe.rb | 6 +-- app/views/ingredients/search.json.jbuilder | 12 +---- db/seeds.rb | 28 +++++----- lib/unit_conversion/unitwise_patch.rb | 33 ++++++------ 17 files changed, 153 insertions(+), 111 deletions(-) create mode 100644 app/models/ingredient.rb diff --git a/app/controllers/calculator_controller.rb b/app/controllers/calculator_controller.rb index e0fe0b4..f2148af 100644 --- a/app/controllers/calculator_controller.rb +++ b/app/controllers/calculator_controller.rb @@ -7,20 +7,27 @@ class CalculatorController < ApplicationController def calculate input = params[:input] output_unit = params[:output_unit] + ingredient_id = params[:ingredient_id] + ingredient = nil density = params[:density] density = nil unless density.present? + if ingredient_id.present? + ingredient = Ingredient.find_by_ingredient_id(ingredient_id) + end + data = {errors: [], output: ''} begin - unit = UnitConversion.parse(input) - if output_unit.present? - unit = unit.convert(output_unit, density) - data[:output] = unit.to_s - else - data[:output] = unit.auto_unit.to_s + UnitConversion::with_custom_units(ingredient ? ingredient.custom_units : []) do + unit = UnitConversion.parse(input) + if output_unit.present? + unit = unit.convert(output_unit, density) + data[:output] = unit.to_s + else + data[:output] = unit.auto_unit.to_s + end end - rescue UnitConversion::UnparseableUnitError => e data[:errors] << e.message end diff --git a/app/controllers/logs_controller.rb b/app/controllers/logs_controller.rb index bf50151..48afd93 100644 --- a/app/controllers/logs_controller.rb +++ b/app/controllers/logs_controller.rb @@ -61,12 +61,12 @@ class LogsController < ApplicationController private def set_log - @log = Log.includes({recipe: {recipe_ingredients: {ingredient: :ingredient_units} }}).find(params[:id]) + @log = Log.includes({recipe: {recipe_ingredients: {food: :food_units} }}).find(params[:id]) end def set_recipe if params[:recipe_id].present? - @recipe = Recipe.includes([{recipe_ingredients: [:ingredient]}]).find(params[:recipe_id]) + @recipe = Recipe.includes([{recipe_ingredients: [:food]}]).find(params[:recipe_id]) end end diff --git a/app/controllers/recipes_controller.rb b/app/controllers/recipes_controller.rb index 71526d3..43d1a40 100644 --- a/app/controllers/recipes_controller.rb +++ b/app/controllers/recipes_controller.rb @@ -81,7 +81,7 @@ class RecipesController < ApplicationController private # Use callbacks to share common setup or constraints between actions. def set_recipe - @recipe = Recipe.includes(recipe_ingredients: {food: :food_units }).find(params[:id]) + @recipe = Recipe.includes(recipe_ingredients: [{food: :food_units }, {recipe_as_ingredient: {recipe_ingredients: {food: :food_units }}}]).find(params[:id]) end # Never trust parameters from the scary internet, only allow the white list through. diff --git a/app/javascript/components/AppRating.vue b/app/javascript/components/AppRating.vue index 2534f18..04e29eb 100644 --- a/app/javascript/components/AppRating.vue +++ b/app/javascript/components/AppRating.vue @@ -1,10 +1,10 @@ @@ -113,6 +113,11 @@ .set { white-space: nowrap; + + svg.iconic { + width: 1.5em; + height: 1.5em; + } } .empty-set { diff --git a/app/javascript/components/RecipeEdit.vue b/app/javascript/components/RecipeEdit.vue index 64b8601..ba17349 100644 --- a/app/javascript/components/RecipeEdit.vue +++ b/app/javascript/components/RecipeEdit.vue @@ -10,10 +10,6 @@
- -
- -
diff --git a/app/javascript/components/TaskItemList.vue b/app/javascript/components/TaskItemList.vue index 3eb9e3c..8d9e185 100644 --- a/app/javascript/components/TaskItemList.vue +++ b/app/javascript/components/TaskItemList.vue @@ -16,19 +16,22 @@ - - - -
- - -
- - {{ i.name }} - {{ i.quantity }} - - - + + + + +
+ + +
+ + {{ i.name }} + {{ i.quantity }} + + +
+ + No Items @@ -73,20 +76,16 @@ }, computed: { + completedTaskItems() { + return (this.taskList ? this.taskList.task_items : []).filter(i => i.completed); + }, + + uncompletedTaskItems() { + return (this.taskList ? this.taskList.task_items : []).filter(i => !i.completed); + }, + taskItems() { - const top = []; - const bottom = []; - const list = (this.taskList ? this.taskList.task_items : []); - - for (let i of list) { - if (!i.completed) { - top.push(i); - } else { - bottom.push(i); - } - } - - return top.concat(bottom); + return this.uncompletedTaskItems.concat(this.completedTaskItems); } }, @@ -148,8 +147,9 @@ margin-bottom: 0; } - div.check .icon { + div.check { border: 2px solid $link; + display: flex; } \ No newline at end of file diff --git a/app/javascript/components/TheCalculator.vue b/app/javascript/components/TheCalculator.vue index 69991fb..293ac86 100644 --- a/app/javascript/components/TheCalculator.vue +++ b/app/javascript/components/TheCalculator.vue @@ -44,7 +44,7 @@
- +
@@ -82,13 +82,13 @@ }, searchItemSelected(ingredient) { - this.ingredient = ingredient; - this.ingredient_name = ingredient.name; - this.density = ingredient.density; + this.ingredient = ingredient || null; + this.ingredient_name = ingredient.name || null; + this.density = ingredient.density || null; }, updateOutput: debounce(function() { - this.loadResource(api.getCalculate(this.input, this.outputUnit, this.density) + this.loadResource(api.getCalculate(this.input, this.outputUnit, this.ingredient ? this.ingredient.ingredient_id : null, this.density) .then(data => { this.output = data.output; this.errors = data.errors; @@ -108,7 +108,7 @@ created() { this.$watch( function() { - return this.input + this.outputUnit + this.density; + return [this.input, this.outputUnit, this.density, this.ingredient]; }, function() { this.updateOutput(); diff --git a/app/javascript/components/TheTaskListList.vue b/app/javascript/components/TheTaskListList.vue index 3ab264c..9061f77 100644 --- a/app/javascript/components/TheTaskListList.vue +++ b/app/javascript/components/TheTaskListList.vue @@ -16,9 +16,9 @@
- - - + + +
@@ -66,6 +66,14 @@ } else { return this.currentTaskList.name; } + }, + + completedItemCount() { + return this.currentTaskList === null ? 0 : this.currentTaskList.task_items.filter(i => i.completed).length; + }, + + uncompletedItemCount() { + return this.currentTaskList === null ? 0 : this.currentTaskList.task_items.filter(i => !i.completed).length; } }, diff --git a/app/javascript/lib/Api.js b/app/javascript/lib/Api.js index a1681b1..4c05040 100644 --- a/app/javascript/lib/Api.js +++ b/app/javascript/lib/Api.js @@ -205,10 +205,11 @@ class Api { return this.get("/ingredients/search", params); } - getCalculate(input, output_unit, density) { + getCalculate(input, output_unit, ingredient_id, density) { const params = { input, output_unit, + ingredient_id, density }; return this.get("/calculator/calculate", params); diff --git a/app/javascript/styles/_transitions.scss b/app/javascript/styles/_transitions.scss index cd9bc7f..8fc0edc 100644 --- a/app/javascript/styles/_transitions.scss +++ b/app/javascript/styles/_transitions.scss @@ -15,7 +15,8 @@ overflow: hidden; } -//.expand-enter, -//.expand-leave-to { -// height: 0; -//} \ No newline at end of file + + +.list-item-move-move { + transition: transform 0.25s; +} \ No newline at end of file diff --git a/app/models/food.rb b/app/models/food.rb index 5e1f4bf..229c034 100644 --- a/app/models/food.rb +++ b/app/models/food.rb @@ -1,4 +1,4 @@ -class Food < ApplicationRecord +class Food < Ingredient include TokenizedLike belongs_to :user @@ -33,18 +33,10 @@ class Food < ApplicationRecord self end - def nutrition_errors - [] - end - def nutrition_unit UnitConversion.parse('100 grams') end - def density? - !density.nil? - end - def ndbn=(value) @usda_food = nil super diff --git a/app/models/ingredient.rb b/app/models/ingredient.rb new file mode 100644 index 0000000..a91dcff --- /dev/null +++ b/app/models/ingredient.rb @@ -0,0 +1,41 @@ +class Ingredient < ApplicationRecord + self.abstract_class = true + + class << self + + def find_by_ingredient_id(ingredient_id) + puts "looking up |#{ingredient_id}|" + case ingredient_id + when /^R(\d+)$/ + puts 'rec' + Recipe.find($1) + when /^F(\d+)$/ + puts 'food' + Food.find($1) + else + raise ActiveRecord::RecordNotFound + end + end + + end + + def ingredient_id + case self + when Recipe + "R#{id}" + when Food + "F#{id}" + else + raise 'Unknown ingredient' + end + end + + def nutrition_errors + [] + end + + def density? + !self.density.nil? + end + +end \ No newline at end of file diff --git a/app/models/nutrition_data.rb b/app/models/nutrition_data.rb index 8abbd19..39c9f23 100644 --- a/app/models/nutrition_data.rb +++ b/app/models/nutrition_data.rb @@ -50,7 +50,7 @@ class NutritionData end unless i.ingredient.nutrition_errors.empty? - @errors << "#{i.name} has errors: #{i.ingredient.nutrition_errors.join(", ")}" + @errors << "#{i.name}: #{i.ingredient.nutrition_errors.join(", ")}" end missing = [] diff --git a/app/models/recipe.rb b/app/models/recipe.rb index c5f21a0..afdfced 100644 --- a/app/models/recipe.rb +++ b/app/models/recipe.rb @@ -1,4 +1,4 @@ -class Recipe < ApplicationRecord +class Recipe < Ingredient include DefaultValues include TokenizedLike @@ -157,10 +157,6 @@ class Recipe < ApplicationRecord end end - def density? - !density.nil? - end - def custom_units arbitrary = self.yields_list.select { |y| !y.mass? && !y.volume? } mass = self.yields_list.select { |y| y.mass? } diff --git a/app/views/ingredients/search.json.jbuilder b/app/views/ingredients/search.json.jbuilder index 9093115..ce8f998 100644 --- a/app/views/ingredients/search.json.jbuilder +++ b/app/views/ingredients/search.json.jbuilder @@ -1,15 +1,7 @@ json.array! @ingredients do |i| - json.extract! i, :name - - case i - when Recipe - json.id "R#{i.id}" - when Food - json.id "F#{i.id}" - else - json.id nil - end + json.extract! i, :ingredient_id, :name, :density + json.id i.ingredient_id end \ No newline at end of file diff --git a/db/seeds.rb b/db/seeds.rb index ef03f4d..bd2d91a 100644 --- a/db/seeds.rb +++ b/db/seeds.rb @@ -12,7 +12,7 @@ puts "Seeding..." dan = User.create!({username: 'dan', full_name: 'Dan', email: 'dan.elbert@gmail.com', password: 'qwerty', password_confirmation: 'qwerty'}) -ingredients = { +foods = { water: {name: 'Water', density: '1 g/ml'}, butter: {name: 'Butter, Salted', ndbn: '01001'}, butter_sal: {name: 'Butter, Unsalted', density: '226 gram/cup'}, @@ -43,8 +43,8 @@ ingredients = { } -ingredients.each do |k, v| - ingredients[k] = Food.create!({user_id: dan.id}.merge(v)) +foods.each do |k, v| + foods[k] = Food.create!({user_id: dan.id}.merge(v)) end g = Recipe.create!({ @@ -69,19 +69,19 @@ bb = Recipe.create!({ bb.tag_names = ['beef', 'dinner', 'stirfry'] [ - {quantity: '1', units: 'pound', preparation: 'flank steak, skirt steak, hanger steak, or flap meat, cut into 1/4-inch thick strips', food: ingredients[:flank]}, - {quantity: '1/4', units: 'cup', preparation: 'divided', food: ingredients[:soy_sauce]}, - {quantity: '1/4', units: 'cup', preparation: 'divided', food: ingredients[:shaoxing]}, - {quantity: '2', units: 'teaspoons', preparation: '', food: ingredients[:cornstarch]}, - {quantity: '1/3', units: 'cup', preparation: '', food: ingredients[:stock]}, - {quantity: '1/4', units: 'cup', preparation: '', food: ingredients[:oyster_sauce]}, - {quantity: '1', units: 'tablespoon', preparation: '', food: ingredients[:sugar]}, - {quantity: '1', units: 'teaspoon', preparation: '', food: ingredients[:seasame_oil]}, - {quantity: '2', units: 'medium cloves', preparation: 'finely minced', food: ingredients[:garlic]}, + {quantity: '1', units: 'pound', preparation: 'flank steak, skirt steak, hanger steak, or flap meat, cut into 1/4-inch thick strips', food: foods[:flank]}, + {quantity: '1/4', units: 'cup', preparation: 'divided', food: foods[:soy_sauce]}, + {quantity: '1/4', units: 'cup', preparation: 'divided', food: foods[:shaoxing]}, + {quantity: '2', units: 'teaspoons', preparation: '', food: foods[:cornstarch]}, + {quantity: '1/3', units: 'cup', preparation: '', food: foods[:stock]}, + {quantity: '1/4', units: 'cup', preparation: '', food: foods[:oyster_sauce]}, + {quantity: '1', units: 'tablespoon', preparation: '', food: foods[:sugar]}, + {quantity: '1', units: 'teaspoon', preparation: '', food: foods[:seasame_oil]}, + {quantity: '2', units: 'medium cloves', preparation: 'finely minced', food: foods[:garlic]}, {quantity: '2', units: 'teaspoons', preparation: 'finely minced', name: 'ginger root'}, {quantity: '3', units: '', preparation: 'whites finely sliced, greens cut into 1/2-inch segments, reserved separately', name: 'Scallions'}, - {quantity: '4', units: 'tablespoons', preparation: '', food: ingredients[:peanut_oil]}, - {quantity: '1', units: 'pound', preparation: '', food: ingredients[:broccoli]}, + {quantity: '4', units: 'tablespoons', preparation: '', food: foods[:peanut_oil]}, + {quantity: '1', units: 'pound', preparation: '', food: foods[:broccoli]}, ].each_with_index do |ri, i| RecipeIngredient.create!({recipe: bb, sort_order: i}.merge(ri)) end diff --git a/lib/unit_conversion/unitwise_patch.rb b/lib/unit_conversion/unitwise_patch.rb index 7f8ffe8..9266459 100644 --- a/lib/unit_conversion/unitwise_patch.rb +++ b/lib/unit_conversion/unitwise_patch.rb @@ -20,23 +20,26 @@ module Unitwise def self.with_custom_units(unit_list, &block) atoms = [] + ret_val = nil - unit_list.each do |u| - atom = Unitwise::Atom.new(u) - atom.validate! - Unitwise::Atom.all.push(atom) - atoms.push(atom) + begin + unit_list.each do |u| + atom = Unitwise::Atom.new(u) + atom.validate! + Unitwise::Atom.all.push(atom) + atoms.push(atom) + end + rem = Unitwise::Expression::Decomposer.send(:reset) + + ret_val = block.call + ensure + atoms.each do |a| + idx = Unitwise::Atom.all.index { |b| b.equal?(a) } + Unitwise::Atom.all.delete_at(idx) + # Unitwise::Atom.all.pop + end + Unitwise::Expression::Decomposer.send(:reset, rem) end - rem = Unitwise::Expression::Decomposer.send(:reset) - - ret_val = block.call - - atoms.each do |a| - idx = Unitwise::Atom.all.index { |b| b.equal?(a) } - Unitwise::Atom.all.delete_at(idx) - # Unitwise::Atom.all.pop - end - Unitwise::Expression::Decomposer.send(:reset, rem) ret_val end