Products allowed in meal plan

This commit is contained in:
Kurt Riddlesperger 2020-01-24 00:56:59 -06:00
parent 5c602ce74e
commit 52698e43b0
4 changed files with 127 additions and 12 deletions

View File

@ -132,6 +132,7 @@ class RecipesController extends BaseController
public function MealPlan(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args)
{
$recipes = $this->Database->recipes()->where('type', RecipesService::RECIPE_TYPE_NORMAL)->fetchAll();
$products = $this->Database->products()->orderBy('name');
$events = array();
foreach($this->Database->meal_plan() as $mealPlanEntry)
@ -141,22 +142,39 @@ class RecipesController extends BaseController
if ($recipe !== null)
{
$title = $recipe->name;
$events[] = array(
'id' => $mealPlanEntry['id'],
'title' => $title,
'start' => $mealPlanEntry['day'],
'date_format' => 'date',
'recipe' => json_encode($recipe),
'mealPlanEntry' => json_encode($mealPlanEntry),
'type' => $mealPlanEntry['type']
);
}
$events[] = array(
'id' => $mealPlanEntry['id'],
'title' => $title,
'start' => $mealPlanEntry['day'],
'date_format' => 'date',
'recipe' => json_encode($recipe),
'mealPlanEntry' => json_encode($mealPlanEntry),
'type' => $mealPlanEntry['type']
);
$product = FindObjectInArrayByPropertyValue($products, 'id', $mealPlanEntry['product_id']);
if ($product !== null)
{
$title = $product->name;
$events[] = array(
'id' => $mealPlanEntry['id'],
'title' => $title,
'start' => $mealPlanEntry['day'],
'date_format' => 'date',
'product' => json_encode($product),
'mealPlanEntry' => json_encode($mealPlanEntry),
'type' => $mealPlanEntry['type']
);
}
}
return $this->AppContainer->view->render($response, 'mealplan', [
'fullcalendarEventSources' => $events,
'recipes' => $recipes,
'products' => $products,
'internalRecipes' => $this->Database->recipes()->whereNot('type', RecipesService::RECIPE_TYPE_NORMAL)->fetchAll(),
'recipesResolved' => $this->RecipesService->GetRecipesResolved()
]);

View File

@ -6,6 +6,7 @@ CREATE TABLE meal_plan (
id INTEGER NOT NULL PRIMARY KEY AUTOINCREMENT UNIQUE,
day DATE NOT NULL,
type TEXT DEFAULT 'recipe',
product_id INTEGER,
recipe_id INTEGER,
recipe_servings INTEGER DEFAULT 1,
note TEXT,

View File

@ -157,6 +157,33 @@ var calendar = $("#calendar").fullCalendar({
}
}
}
if (event.type == "product")
{
var product = JSON.parse(event.product);
if (product === null || product === undefined)
{
return false;
}
element.attr("data-product", event.product);
var productConsumeButtonDisabledClasses = "";
element.html('\
<div> \
<h5 class="text-truncate">' + product.name + '<h5> \
<h5 class="small text-truncate">' + __n(mealPlanEntry.recipe_servings, "%s serving", "%s servings") + '</h5> \
<h5> \
<a class="ml-1 btn btn-outline-danger btn-xs remove-recipe-button" href="#"><i class="fas fa-trash"></i></a> \
<a class="ml-1 btn btn-outline-success btn-xs product-consume-button ' + productConsumeButtonDisabledClasses + '" href="#" data-toggle="tooltip" title="' + __t("Consume product") + '" data-product-id="' + product.id.toString() + '" data-product-name="' + product.name + '" data-servings-amount="' + mealPlanEntry.recipe_servings + '"><i class="fas fa-utensils"></i></a> \
</h5> \
</div>');
if (product.picture_file_name && !product.picture_file_name.isEmpty())
{
element.html(element.html() + '<div class="mx-auto"><img data-src="' + U("/api/files/productpictures/") + btoa(product.picture_file_name) + '?force_serve_as=picture&best_fit_width=400" class="img-fluid lazy"></div>')
}
}
else if (event.type == "note")
{
element.html('\
@ -254,7 +281,18 @@ $('#save-add-recipe-button').on('click', function(e)
return false;
}
Grocy.Api.Post('objects/meal_plan', $('#add-recipe-form').serializeJSON(),
var jsonData = $('#add-recipe-form').serializeJSON();
if (Grocy.Components.RecipePicker.GetValue() != "")
{
jsonData.type = "recipe";
}
else if (Grocy.Components.ProductPicker.GetValue() != "")
{
jsonData.type = "product";
}
Grocy.Api.Post('objects/meal_plan', jsonData,
function(result)
{
window.location.reload();
@ -376,6 +414,45 @@ $(document).on('click', '.recipe-order-missing-button', function(e)
});
});
$(document).on('click', '.product-consume-button', function(e)
{
e.preventDefault();
// Remove the focus from the current button
// to prevent that the tooltip stays until clicked anywhere else
document.activeElement.blur();
Grocy.FrontendHelpers.BeginUiBusy();
var productId = $(e.currentTarget).attr('data-product-id');
var consumeAmount = $(e.currentTarget).attr('data-servings-amount');
Grocy.Api.Post('stock/products/' + productId + '/consume', { 'amount': consumeAmount, 'spoiled': false },
function(bookingResponse)
{
Grocy.Api.Get('stock/products/' + productId,
function(result)
{
var toastMessage = __t('Removed %1$s of %2$s from stock', consumeAmount.toString() + " " + __n(consumeAmount, result.quantity_unit_stock.name, result.quantity_unit_stock.name_plural), result.product.name) + '<br><a class="btn btn-secondary btn-sm mt-2" href="#" onclick="UndoStockTransaction(\'' + bookingResponse.transaction_id + '\')"><i class="fas fa-undo"></i> ' + __t("Undo") + '</a>';
Grocy.FrontendHelpers.EndUiBusy();
toastr.success(toastMessage);
},
function(xhr)
{
Grocy.FrontendHelpers.EndUiBusy();
console.error(xhr);
}
);
},
function(xhr)
{
Grocy.FrontendHelpers.EndUiBusy();
console.error(xhr);
}
);
});
$(document).on('click', '.recipe-consume-button', function(e)
{
// Remove the focus from the current button
@ -461,3 +538,16 @@ $(window).on("resize", function()
calendar.fullCalendar("changeView", "basicWeek");
}
});
function UndoStockTransaction(transactionId)
{
Grocy.Api.Post('stock/transactions/' + transactionId.toString() + '/undo', { },
function (result)
{
toastr.success(__t("Transaction successfully undone"));
},
function (xhr)
{
console.error(xhr);
}
);
};

View File

@ -45,7 +45,14 @@
@include('components.recipepicker', array(
'recipes' => $recipes,
'isRequired' => true,
'isRequired' => false,
'nextInputSelector' => '#recipe_servings'
))
@include('components.productpicker', array(
'products' => $products,
'isRequired' => false,
'disallowAllProductWorkflows' => true,
'nextInputSelector' => '#recipe_servings'
))
@ -58,7 +65,6 @@
))
<input type="hidden" id="day" name="day" value="">
<input type="hidden" name="type" value="recipe">
</form>
</div>