Source waters are fixed, removed grid editor. Redesigned the water screen. Made a simple visual if water treatments are out of range. Water mixer for standard and dillute water works. Swapped the mash and water tabs.

Wed, 19 Dec 2018 21:58:21 +0100

author
Michiel Broek <mbroek@mbse.eu>
date
Wed, 19 Dec 2018 21:58:21 +0100
changeset 148
c0f0bbfefd63
parent 147
e6e5d007eb54
child 149
ff45488d480e

Source waters are fixed, removed grid editor. Redesigned the water screen. Made a simple visual if water treatments are out of range. Water mixer for standard and dillute water works. Swapped the mash and water tabs.

www/import/from_brouwhulp.php file | annotate | diff | comparison | revisions
www/includes/db_recipes.php file | annotate | diff | comparison | revisions
www/js/global.js file | annotate | diff | comparison | revisions
www/js/rec_edit.js file | annotate | diff | comparison | revisions
www/rec_edit.php file | annotate | diff | comparison | revisions
--- a/www/import/from_brouwhulp.php	Mon Dec 17 22:24:32 2018 +0100
+++ b/www/import/from_brouwhulp.php	Wed Dec 19 21:58:21 2018 +0100
@@ -722,35 +722,31 @@
 
 function recipe_waters($recipe, $db)
 {
-	$waters = "[";
-	$comma = FALSE;
+	$waters = "";
+	$index = 0;
 	foreach ($recipe->WATERS->WATER as $water) {
-		if ($comma)
-			$waters .= ',';
-		$comma = TRUE;
-		$waters .= '{"w_name":"' . mysqli_real_escape_string($db, $water->NAME) . '"';
-		$waters .= ',"w_amount":' . floatval($water->AMOUNT);
+		$index++;
+		$waters .= "', w" . $index . "_name='" . mysqli_real_escape_string($db, $water->NAME);
+		$waters .= "', w" . $index . "_amount='" . floatval($water->AMOUNT);
 		if ($water->CALCIUM)
-		$waters .= ',"w_calcium":' . floatval($water->CALCIUM);
+		$waters .= "', w" . $index . "_calcium='" . floatval($water->CALCIUM);
 		if ($water->SULFATE)
-		$waters .= ',"w_sulfate":' . floatval($water->SULFATE);
+		$waters .= "', w" . $index . "_sulfate='" . floatval($water->SULFATE);
 		if ($water->CHLORIDE)
-		$waters .= ',"w_chloride":' . floatval($water->CHLORIDE);
+		$waters .= "', w" . $index . "_chloride='" . floatval($water->CHLORIDE);
 		if ($water->SODIUM)
-		$waters .= ',"w_sodium":' . floatval($water->SODIUM);
+		$waters .= "', w" . $index . "_sodium='" . floatval($water->SODIUM);
 		if ($water->MAGNESIUM)
-		$waters .= ',"w_magnesium":' . floatval($water->MAGNESIUM);
+		$waters .= "', w" . $index . "_magnesium='" . floatval($water->MAGNESIUM);
 		if ($water->PH)
-		$waters .= ',"w_ph":' . floatval($water->PH);
+		$waters .= "', w" . $index . "_ph='" . floatval($water->PH);
 		if ($water->TOTAL_ALKALINITY)
-		$waters .= ',"w_total_alkalinity":' . floatval($water->TOTAL_ALKALINITY);
+		$waters .= "', w" . $index . "_total_alkalinity='" . floatval($water->TOTAL_ALKALINITY);
 		if ($water->COST)
-		$waters .= ',"w_cost":' . floatval($water->COST);
+		$waters .= "', w" . $index . "_cost='" . floatval($water->COST);
 		else
-		$waters .= ',"w_cost":0.00';
-		$waters .= "}";
+		$waters .= "', w" . $index . "_cost='0";
 	}
-	$waters .= ']';
 	return $waters;
 }
 
@@ -792,7 +788,6 @@
 	$len_hops = 0;
 	$len_miscs = 0;
 	$len_yeasts = 0;
-	$len_waters = 0;
 	$len_mash = 0;
 
 	echo "  Start adding recipes to the database\n";
@@ -913,13 +908,10 @@
 		}
 
 		/*
-		 * Put the waters in a json array
+		 * Get the waters
 		 */
 		if ($recipe->WATERS) {
-			$waters = recipe_waters($recipe, $db);
-			$sql .= "', json_waters='" . $waters;
-			if (strlen($waters) > $len_waters)
-				$len_waters = strlen($waters);
+			$sql .= recipe_waters($recipe, $db);
 		}
 
 		/*
@@ -960,7 +952,6 @@
 //	echo "Hops:         " . $len_hops . PHP_EOL;
 //	echo "Miscs:        " . $len_miscs . PHP_EOL;
 //	echo "Yeasts:       " . $len_yeasts . PHP_EOL;
-//	echo "Waters:       " . $len_waters . PHP_EOL;
 //	echo "Mash:         " . $len_mash . PHP_EOL;
 }
 
@@ -973,7 +964,6 @@
         $len_hops = 0;
         $len_miscs = 0;
         $len_yeasts = 0;
-        $len_waters = 0;
         $len_mash = 0;
 
         echo "  Start adding brews to the database\n";
@@ -1107,13 +1097,10 @@
                 }
 
                 /*
-                 * Put the waters in a json array
+                 * Get the waters
                  */
                 if ($recipe->WATERS) {
-                        $waters = recipe_waters($recipe, $db);
-                        $rsql .= "', json_waters='" . $waters;
-                        if (strlen($waters) > $len_waters)
-                                $len_waters = strlen($waters);
+                        $rsql .= recipe_waters($recipe, $db);
                 }
 
                 /*
--- a/www/includes/db_recipes.php	Mon Dec 17 22:24:32 2018 +0100
+++ b/www/includes/db_recipes.php	Wed Dec 19 21:58:21 2018 +0100
@@ -68,6 +68,30 @@
 	$sql .= "', mash_ph='" . $_POST['mash_ph'];
 	$sql .= "', mash_name='" . $_POST['mash_name'];
 	$sql .= "', calc_acid='" . $_POST['calc_acid'];
+	if (isset($_POST['w1_name'])) {
+		$sql .= "', w1_name='" . mysqli_real_escape_string($connect, $_POST['w1_name']);
+		$sql .= "', w1_amount='" . $_POST['w1_amount'];
+		$sql .= "', w1_calcium='" . $_POST['w1_calcium'];
+		$sql .= "', w1_sulfate='" . $_POST['w1_sulfate'];
+		$sql .= "', w1_chloride='" . $_POST['w1_chloride'];
+		$sql .= "', w1_sodium='" . $_POST['w1_sodium'];
+		$sql .= "', w1_magnesium='" . $_POST['w1_magnesium'];
+		$sql .= "', w1_total_alkalinity='" . $_POST['w1_total_alkalinity'];
+		$sql .= "', w1_ph='" . $_POST['w1_ph'];
+		$sql .= "', w1_cost='" . $_POST['w1_cost'];
+	}
+	if (isset($_POST['w2_name'])) {
+		$sql .= "', w2_name='" . mysqli_real_escape_string($connect, $_POST['w2_name']);
+		$sql .= "', w2_amount='" . $_POST['w2_amount'];
+		$sql .= "', w2_calcium='" . $_POST['w2_calcium'];
+		$sql .= "', w2_sulfate='" . $_POST['w2_sulfate'];
+		$sql .= "', w2_chloride='" . $_POST['w2_chloride'];
+		$sql .= "', w2_sodium='" . $_POST['w2_sodium'];
+		$sql .= "', w2_magnesium='" . $_POST['w2_magnesium'];
+		$sql .= "', w2_total_alkalinity='" . $_POST['w2_total_alkalinity'];
+		$sql .= "', w2_ph='" . $_POST['w2_ph'];
+		$sql .= "', w2_cost='" . $_POST['w2_cost'];
+	}
 	syslog(LOG_NOTICE, $sql);
 
 	if (isset($_POST['fermentables'])) {
@@ -114,17 +138,6 @@
 		$sql .= "', json_yeasts='" . str_replace($rescapers,$rreplacements,json_encode($array));
 	}
 
-	if (isset($_POST['waters'])) {
-		$array = $_POST['waters'];
-		foreach($array as $key => $item){
-			foreach ($disallowed as $disallowed_key) {
-				unset($array[$key]["$disallowed_key"]);
-			}
-		}
-		syslog(LOG_NOTICE, "json_waters: ".str_replace($rescapers,$rreplacements,json_encode($array)));
-		$sql .= "', json_waters='" . str_replace($rescapers,$rreplacements,json_encode($array));
-	}
-
 	if (isset($_POST['mashs'])) {
 		$array = $_POST['mashs'];
 		foreach($array as $key => $item){
@@ -228,11 +241,30 @@
 		$recipes .= ',"mash_ph":' . $row['mash_ph'];
 		$recipes .= ',"mash_name":"' . $row['mash_name'];
 		$recipes .= '","calc_acid":' . $row['calc_acid'];
+		$recipes .= ',"w1_name":"' . str_replace($escapers, $replacements, $row['w1_name']);
+		$recipes .= '","w1_amount":' . $row['w1_amount'];
+		$recipes .= ',"w1_calcium":' . $row['w1_calcium'];
+		$recipes .= ',"w1_sulfate":' . $row['w1_sulfate'];
+		$recipes .= ',"w1_chloride":' . $row['w1_chloride'];
+		$recipes .= ',"w1_sodium":' . $row['w1_sodium'];
+		$recipes .= ',"w1_magnesium":' . $row['w1_magnesium'];
+		$recipes .= ',"w1_total_alkalinity":' . $row['w1_total_alkalinity'];
+		$recipes .= ',"w1_ph":' . $row['w1_ph'];
+		$recipes .= ',"w1_cost":' . $row['w1_cost'];
+		$recipes .= ',"w2_name":"' . str_replace($escapers, $replacements, $row['w2_name']);
+		$recipes .= '","w2_amount":' . $row['w2_amount'];
+		$recipes .= ',"w2_calcium":' . $row['w2_calcium'];
+		$recipes .= ',"w2_sulfate":' . $row['w2_sulfate'];
+		$recipes .= ',"w2_chloride":' . $row['w2_chloride'];
+		$recipes .= ',"w2_sodium":' . $row['w2_sodium'];
+		$recipes .= ',"w2_magnesium":' . $row['w2_magnesium'];
+		$recipes .= ',"w2_total_alkalinity":' . $row['w2_total_alkalinity'];
+		$recipes .= ',"w2_ph":' . $row['w2_ph'];
+		$recipes .= ',"w2_cost":' . $row['w2_cost'];
 		$recipes .= ',"fermentables":' . $row['json_fermentables'];
 		$recipes .= ',"hops":' . $row['json_hops'];
 		$recipes .= ',"miscs":' . $row['json_miscs'];
 		$recipes .= ',"yeasts":' . $row['json_yeasts'];
-		$recipes .= ',"waters":' . $row['json_waters'];
 		$recipes .= ',"mashs":' . $row['json_mashs'];
 		$recipes .= '}';
 	}
--- a/www/js/global.js	Mon Dec 17 22:24:32 2018 +0100
+++ b/www/js/global.js	Wed Dec 19 21:58:21 2018 +0100
@@ -579,6 +579,7 @@
  *
  *
  * HCO3 = CaCo3 x 1,22
+ * CaCO3) = HCO3- x 50 / 61
  * 1°F = 10mg/L CaCo3
  */
 
--- a/www/js/rec_edit.js	Mon Dec 17 22:24:32 2018 +0100
+++ b/www/js/rec_edit.js	Wed Dec 19 21:58:21 2018 +0100
@@ -44,7 +44,6 @@
 
 $(document).ready(function () {
 
-	var	dataRecord = {};
 	var	to_100 = false;	// Fermentables adjust to 100%
 	var	preboil_sg = 0;
 	var	sugarsm = 0;	// Sugars after mash
@@ -54,6 +53,7 @@
 	var	svg = 77;	// Default attenuation
 	var	hop_flavour = 0;
 	var	hop_aroma = 0;
+	var	mash_infuse = 0;
 
 	console.log("record:" + my_record + "  return:" + my_return + "  theme:" + theme);
 	$("#jqxLoader").jqxLoader({
@@ -175,10 +175,20 @@
 	}
 
 
+	function setRangeIndicator(ion, rangeCode) {
+		$("#wr_" + ion).html("<img src='images/checkmark_range_" + rangeCode + ".gif'><span style='font-size: 10px; font-style: italic;'>" + rangeCode + "</span>");
+	}
+
+	function mix(v1, v2, c1, c2) {
+		if ((v1 + v2) > 0) {
+			return ((v1 * c1) + (v2 * c2)) / (v1 + v2);
+		}
+		return 0;
+	}
+
 	function calcWater() {
 
 		console.log("calcWater()");
-		var rows = $('#waterGrid').jqxGrid('getrows');
 		var liters = 0;
 		var calcium = 0;
 		var magnesium = 0;
@@ -187,29 +197,66 @@
 		var chloride = 0;
 		var sulfate = 0;
 		var ph = 0;
-		for (var i = 0; i < rows.length; i++) {
-			var row = rows[i];
-			liters += row.w_amount;
-			calcium += row.w_amount * row.w_calcium;
-			magnesium += row.w_amount * row.w_magnesium;
-			sodium += row.w_amount * row.w_sodium;
-			total_alkalinity += row.w_amount * row.w_total_alkalinity;
-			chloride += row.w_amount * row.w_chloride;
-			sulfate += row.w_amount * row.w_sulfate;
-			ph += Math.pow(10, -row.w_ph) * row.w_amount;
+
+//		console.log((dataRecord.w1_name != "") + " " + (dataRecord.w2_name != ""));
+		if (dataRecord.w1_name != "") {
+			if (dataRecord.w2_name != "") {
+				liters = dataRecord.w1_amount + dataRecord.w2_amount;
+				calcium = Math.round(mix(dataRecord.w1_amount, dataRecord.w2_amount, dataRecord.w1_calcium, dataRecord.w2_calcium) * 10) / 10;
+				magnesium = Math.round(mix(dataRecord.w1_amount, dataRecord.w2_amount, dataRecord.w1_magnesium, dataRecord.w2_magnesium) * 10) / 10;
+				sodium = Math.round(mix(dataRecord.w1_amount, dataRecord.w2_amount, dataRecord.w1_sodium, dataRecord.w2_sodium) * 10) / 10;
+				chloride = Math.round(mix(dataRecord.w1_amount, dataRecord.w2_amount, dataRecord.w1_chloride, dataRecord.w2_chloride) * 10) / 10;
+				sulfate = Math.round(mix(dataRecord.w1_amount, dataRecord.w2_amount, dataRecord.w1_sulfate, dataRecord.w2_sulfate) * 10) / 10;
+				total_alkalinity = Math.round(mix(dataRecord.w1_amount, dataRecord.w2_amount, dataRecord.w1_total_alkalinity, dataRecord.w2_total_alkalinity) * 10) / 10;
+				ph = Math.round(-Math.log10(((Math.pow(10, -dataRecord.w1_ph) * dataRecord.w1_amount) + (Math.pow(10, -dataRecord.w2_ph) * dataRecord.w2_amount))  / liters) * 10) / 10;
+			} else {
+				liters = dataRecord.w1_amount;
+				calcium = dataRecord.w1_calcium;
+				magnesium = dataRecord.w1_magnesium;
+				sodium = dataRecord.w1_sodium;
+				chloride = dataRecord.w1_chloride;
+				sulfate = dataRecord.w1_sulfate;
+				total_alkalinity = dataRecord.total_alkalinity;
+				ph = dataRecord.w1_ph;
+			}
 		}
-		$('#wg_volume').val(liters);
-		calcium = Math.round(calcium / liters * 10) / 10;
+		$('#wg_amount').val(liters);
 		$('#wg_calcium').val(calcium);
-		$('#wg_magnesium').val(Math.round(magnesium / liters * 10) / 10);
-		$('#wg_sodium').val(Math.round(sodium / liters * 10) / 10);
-		$('#wg_total_alkalinity').val(Math.round(total_alkalinity / liters * 10) / 10);
-		$('#wg_chloride').val(Math.round(chloride / liters * 10) / 10);
-		sulfate = Math.round(sulfate / liters * 10) / 10;
+		$('#wg_magnesium').val(magnesium);
+		$('#wg_sodium').val(sodium);
+		$('#wg_total_alkalinity').val(total_alkalinity);
+		$('#wg_chloride').val(chloride);
 		$('#wg_sulfate').val(sulfate);
 		// Note: brouwhulp has the malts included here in the result.
-		ph = Math.round(-Math.log10(ph / liters) * 10) / 10;
 		$('#wg_ph').val(ph);
+
+		// Brouwhulp < 40 || > 200
+		if (calcium < 50) { setRangeIndicator("calcium", "low"); }
+		if (calcium >= 50 && calcium <= 150) { setRangeIndicator("calcium", "normal"); }
+		if (calcium > 150) { setRangeIndicator("calcium", "high"); }
+		if (calcium > 250) { setRangeIndicator("calcium", "harmful"); }
+
+		// Brouwhulp > 40
+		if (magnesium >= 0 && magnesium <= 30) { setRangeIndicator("magnesium", "normal"); }
+		if (magnesium > 30) { setRangeIndicator("magnesium", "high"); }
+		if (magnesium > 50) { setRangeIndicator("magnesium", "harmful"); }
+
+		// Brouwhulp > 100
+		if (sodium <= 150) { setRangeIndicator("sodium", "normal"); }
+		if (sodium > 150) { setRangeIndicator("sodium", "high"); }
+		if (sodium > 200) { setRangeIndicator("sodium", "harmful"); }
+
+		// Brouwhulp > 200
+		if (chloride <= 250) { setRangeIndicator("chloride", "normal"); }
+		if (chloride > 250) { setRangeIndicator("chloride", "high"); }
+		if (chloride > 300) { setRangeIndicator("chloride", "harmful"); }
+
+		// Brouwhulp > 600
+		if (sulfate < 50) { setRangeIndicator("sulfate", "low"); }
+		if (sulfate >= 50 && sulfate <= 350) { setRangeIndicator("sulfate", "normal"); }
+		if (sulfate > 350) { setRangeIndicator("sulfate", "high"); }
+		if (sulfate > 750) { setRangeIndicator("sulfate", "harmful"); }
+
 	}
 
 	function calcFermentablesFromOG(OG) {
@@ -249,6 +296,23 @@
 	function calcInit () {
 		console.log("calc.init()");
 
+		$("#w1_name").jqxDropDownList('selectItem', dataRecord.w1_name);
+		$("#w2_name").jqxDropDownList('selectItem', dataRecord.w2_name);
+		calcWater();
+		$("#w2_amount").on('change', function (event) {
+			var newval = parseFloat(event.args.value);
+
+			if (newval > mash_infuse) {
+				$("#w2_amount").val(dataRecord.w2_amount);
+				return;
+			}
+			dataRecord.w1_amount = parseFloat($("#wg_amount").jqxNumberInput('decimal')) - newval;
+			$("#w1_amount").val(dataRecord.w1_amount);
+			dataRecord.w2_amount = newval;
+			console.log("new: "+event.args.value+" w1: "+dataRecord.w1_amount+"  w2: "+dataRecord.w2_amount);
+			calcWater();
+		});
+
 		$('#color_method').on('change', function (event) { calcFermentables(); });
 		$('#ibu_method').on('change', function (event) {
 			calcFermentables();
@@ -343,6 +407,7 @@
 		}
 	});
 
+	var dataRecord = {};
 	var url = "includes/db_recipes.php";
 	// tooltips
 	$("#name").jqxTooltip({ content: 'De naam voor dit recept.' });
@@ -429,11 +494,30 @@
 			{ name: 'mash_ph', type: 'float' },
 			{ name: 'mash_name', type: 'string' },
 			{ name: 'calc_acid', type: 'bool' },
+			{ name: 'w1_name', type: 'string' },
+			{ name: 'w1_amount', type: 'float' },
+			{ name: 'w1_calcium', type: 'float' },
+			{ name: 'w1_sulfate', type: 'float' },
+			{ name: 'w1_chloride', type: 'float' },
+			{ name: 'w1_sodium', type: 'float' },
+			{ name: 'w1_magnesium', type: 'float' },
+			{ name: 'w1_total_alkalinity', type: 'float' },
+			{ name: 'w1_ph', type: 'float' },
+			{ name: 'w1_cost', type: 'float' },
+			{ name: 'w2_name', type: 'string' },
+			{ name: 'w2_amount', type: 'float' },
+			{ name: 'w2_calcium', type: 'float' },
+			{ name: 'w2_sulfate', type: 'float' },
+			{ name: 'w2_chloride', type: 'float' },
+			{ name: 'w2_sodium', type: 'float' },
+			{ name: 'w2_magnesium', type: 'float' },
+			{ name: 'w2_total_alkalinity', type: 'float' },
+			{ name: 'w2_ph', type: 'float' },
+			{ name: 'w2_cost', type: 'float' },
 			{ name: 'fermentables', type: 'array' },
 			{ name: 'hops', type: 'string' },
 			{ name: 'miscs', type: 'string' },
 			{ name: 'yeasts', type: 'string' },
-			{ name: 'waters', type: 'array' },
 			{ name: 'mashs', type: 'string' }
 		],
 		id: 'record',
@@ -490,11 +574,30 @@
 			$("#sparge_acid_perc").val(dataRecord.sparge_acid_perc);
 			$("#sparge_acid_amount").val(dataRecord.sparge_acid_amount);
 			$("#calc_acid").val(dataRecord.calc_acid);
+			$("#w1_name").val(dataRecord.w1_name);
+			$("#w1_amount").val(dataRecord.w1_amount);
+			$("#w1_calcium").val(dataRecord.w1_calcium);
+			$("#w1_sulfate").val(dataRecord.w1_sulfate);
+			$("#w1_chloride").val(dataRecord.w1_chloride);
+			$("#w1_sodium").val(dataRecord.w1_sodium);
+			$("#w1_magnesium").val(dataRecord.w1_magnesium);
+			$("#w1_total_alkalinity").val(dataRecord.w1_total_alkalinity);
+			$("#w1_ph").val(dataRecord.w1_ph);
+			$("#w1_cost").val(dataRecord.w1_cost);
+			$("#w2_name").val(dataRecord.w2_name);
+			$("#w2_amount").val(dataRecord.w2_amount);
+			$("#w2_calcium").val(dataRecord.w2_calcium);
+			$("#w2_sulfate").val(dataRecord.w2_sulfate);
+			$("#w2_chloride").val(dataRecord.w2_chloride);
+			$("#w2_sodium").val(dataRecord.w2_sodium);
+			$("#w2_magnesium").val(dataRecord.w2_magnesium);
+			$("#w2_total_alkalinity").val(dataRecord.w2_total_alkalinity);
+			$("#w2_ph").val(dataRecord.w2_ph);
+			$("#w2_cost").val(dataRecord.w2_cost);
 			editFermentable(dataRecord);
 			editHop(dataRecord);
 			editMisc(dataRecord);
 			editYeast(dataRecord);
-			editWater(dataRecord);
 			editMash(dataRecord);
 			$('#jqxTabs').jqxTabs('next');
 		},
@@ -1398,129 +1501,6 @@
 		});
         };
 
-	// Inline waters editor
-	var editWater = function (data) {
-		var waterSource = {
-			localdata: data.waters,
-			datatype: "local",
-			datafields: [
-				{ name: 'w_name', type: 'string' },
-				{ name: 'w_amount', type: 'float' },
-				{ name: 'w_calcium', type: 'float' },
-				{ name: 'w_sulfate', type: 'float' },
-				{ name: 'w_chloride', type: 'float' },
-				{ name: 'w_sodium', type: 'float' },
-				{ name: 'w_magnesium', type: 'float' },
-				{ name: 'w_ph', type: 'float' },
-				{ name: 'w_total_alkalinity', type: 'float' },
-				{ name: 'w_cost', type: 'float' },
-			],
-			addrow: function (rowid, rowdata, position, commit) {
-				commit(true);
-			},
-			deleterow: function (rowid, commit) {
-				commit(true);
-			}
-		};
-		var waterAdapter = new $.jqx.dataAdapter(waterSource);
-		$("#waterGrid").jqxGrid({
-			width: 960,
-			height: 200,
-			source: waterAdapter,
-			theme: theme,
-			selectionmode: 'singlerow',
-			editmode: 'selectedcell',
-			editable: true,
-			localization: getLocalization(),
-			showtoolbar: true,
-			rendertoolbar: function (toolbar) {
-				var me = this;
-				var container = $("<div style='overflow: hidden; position: relative; margin: 5px;'></div>");
-				toolbar.append(container);
-				container.append('<div style="float: left; margin-left: 165px;" id="waddrowbutton"></div>');
-				container.append('<div style="float: left; margin-left: 10px; margin-top: 5px;">In voorraad:</div>');
-				container.append('<div style="float: left; margin-left: 10px;" id="winstockbutton"></div>');
-				container.append('<input style="float: left; margin-left: 200px;" id="wdeleterowbutton" type="button" value="Verwijder water" />');
-				// add water from dropdownlist.
-				$("#waddrowbutton").jqxDropDownList({
-					placeHolder: "Kies water:",
-					theme: theme,
-					source: waterlist,
-					displayMember: "name",
-					width: 150,
-					height: 27,
-					dropDownWidth: 400,
-					dropDownHeight: 400
-				});
-				$("#waddrowbutton").on('select', function (event) {
-					if (event.args) {
-						var index = event.args.index;
-						var datarecord = waterlist.records[index];
-						var row = {};
-						row["w_name"] = datarecord.name;
-						row["w_amount"] = 0;
-						row["w_calcium"] = datarecord.calcium;
-						row["w_sulfate"] = datarecord.sulfate;
-						row["w_chloride"] = datarecord.chloride;
-						row["w_sodium"] = datarecord.sodium;
-						row["w_magnesium"] = datarecord.magnesium;
-						row["w_ph"] = datarecord.ph;
-						row["w_total_alkalinity"] = datarecord.total_alkalinity;
-						row["w_cost"] = datarecord.cost;
-						var commit = $("#waterGrid").jqxGrid('addrow', null, row);
-					}
-				});
-				$("#winstockbutton").jqxCheckBox({ theme: theme, height: 27 });
-				$("#winstockbutton").on('change', function (event) {
-					waterinstock = event.args.checked;
-					waterlist.dataBind();
-				});
-				// delete selected water.
-				// Overgebleven waters in volume verhogen met het verwijderde water.
-				$("#wdeleterowbutton").jqxButton({ theme: theme, height: 27, width: 150 });
-				$("#wdeleterowbutton").on('click', function () {
-					var selectedrowindex = $("#waterGrid").jqxGrid('getselectedrowindex');
-					var rowscount = $("#waterGrid").jqxGrid('getdatainformation').rowscount;
-					if (selectedrowindex >= 0 && selectedrowindex < rowscount) {
-						var id = $("#waterGrid").jqxGrid('getrowid', selectedrowindex);
-						var commit = $("#waterGrid").jqxGrid('deleterow', id);
-					}
-					calcWater();
-				});
-			},
-			ready: function() {
-				calcWater();
-				$('#jqxTabs').jqxTabs('next');
-			},
-			columns: [
-				{ text: 'Water bron', editable: false, datafield: 'w_name' },
-				{ text: 'Volume', datafield: 'w_amount', width: 80, align: 'right', cellsalign: 'right', cellsformat: 'f1', 
-				  columntype: 'numberinput',
-				  validation: function (cell, value) {
-					if (value < 0 || value > 100000000000 ) {
-						return { result: false, message: "Volume moet  0-~ zijn" };
-					}
-					return true;
-				  }
-			       	},
-				// TODO: validator test max is hoeveelheid maischwater. Dan water verdelen voor totaal.
-				{ text: 'Ca', editable: false, datafield: 'w_calcium', width: 80, align: 'right', cellsalign: 'right', cellsformat: 'f1' },
-				{ text: 'Mg', editable: false, datafield: 'w_magnesium', width: 80, align: 'right', cellsalign: 'right', cellsformat: 'f1' },
-				{ text: 'Na', editable: false, datafield: 'w_sodium', width: 80, align: 'right', cellsalign: 'right', cellsformat: 'f1' },
-				{ text: 'Tot Alk', editable: false, datafield: 'w_total_alkalinity', width: 80, align: 'right', cellsalign: 'right', cellsformat: 'f1' },
-				{ text: 'CaSO4', editable: false, datafield: 'w_sulfate', width: 80, align: 'right', cellsalign: 'right', cellsformat: 'f1' },
-				{ text: 'Cl', editable: false, datafield: 'w_chloride', width: 80, align: 'right', cellsalign: 'right', cellsformat: 'f1' },
-				{ text: 'pH', editable: false, datafield: 'w_ph', width: 80, align: 'right', cellsalign: 'right', cellsformat: 'f1' }
-			]
-		});
-		$("#waterGrid").on('cellendedit', function (event) {
-			var args = event.args;
-			console.log("Event Type: cellendedit, Column: " + args.datafield + ", Row: " + (args.rowindex) + ", Value: " + args.value);
-			$("#waterGrid").jqxGrid('setcellvalue', args.rowindex, args.datafield, args.value);
-			calcWater();
-		});
-	};
-
 	// inline mash editor
         var editMash = function (data) {
 		var generaterow = function () {
@@ -1554,7 +1534,17 @@
                                 commit(true);
                         }
                 };
-                var mashAdapter = new $.jqx.dataAdapter(mashSource);
+                var mashAdapter = new $.jqx.dataAdapter(mashSource, {
+			beforeLoadComplete: function (records) {
+				mash_infuse = 0;
+				var data = new Array();
+				for (var i = 0; i < records.length; i++) {
+					var row = records[i];
+					if (row.step_type == 'Infusion')
+						mash_infuse += parseFloat(row.step_infuse_amount);
+				}
+			},	
+		});
                 $("#mashGrid").jqxGrid({
                         width: 960,
                         height: 400,
@@ -1702,13 +1692,100 @@
 	$("#mash_name").jqxInput({ theme: theme, width: 320, height: 23 });
 	$("#mash_ph").jqxNumberInput({ inputMode: 'simple', spinMode: 'simple', theme: theme, width: 100, height: 23, min: 4, max: 8, decimalDigits: 1, spinButtons: true, spinButtonsStep: 0.1 });
 	$("#tgt_mash_ph").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 100, height: 23, decimalDigits: 1, readOnly: true });
-	$("#mash_sparge_temp").jqxNumberInput({ inputMode: 'simple', spinMode: 'simple', theme: theme, width: 100, height: 23, min: 70, max: 98, decimalDigits: 1, spinButtons: true, spinButtonsStep: 0.5 });
+	$("#sparge_temp").jqxNumberInput({ inputMode: 'simple', spinMode: 'simple', theme: theme, width: 100, height: 23, min: 70, max: 98, decimalDigits: 1, spinButtons: true, spinButtonsStep: 0.5 });
 	// Hop flavour and aroma gauges
 	$("#hop_flavour").jqxProgressBar({ width: 300, height: 23, theme: theme, showText: true });
 	$("#hop_aroma").jqxProgressBar({ width: 300, height: 23, theme: theme, showText: true });
 
 	// Water treatment
-	$("#wg_volume").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w1_name").jqxDropDownList({
+		placeHolder: "Kies hoofd water:",
+		theme: theme,
+		source: waterlist,
+		displayMember: "name",
+		width: 250,
+		height: 27,
+		dropDownWidth: 400,
+		dropDownHeight: 400
+	});
+	$("#w1_name").on('select', function (event) {
+		if (event.args) {
+			var index = event.args.index;
+			var datarecord = waterlist.records[index];
+			dataRecord.w1_name = datarecord.name;
+			$("#w1_calcium").val(datarecord.calcium);
+			dataRecord.w1_calcium = datarecord.calcium;
+			$("#w1_sulfate").val(datarecord.sulfate);
+			dataRecord.w1_sulfate = datarecord.sulfate;
+			$("#w1_chloride").val(datarecord.chloride);
+			dataRecord.w1_chloride = datarecord.chloride;
+			$("#w1_sodium").val(datarecord.sodium);
+			dataRecord.w1_sodium = datarecord.sodium;
+			$("#w1_magnesium").val(datarecord.magnesium);
+			dataRecord.w1_magnesium = datarecord.magnesium;
+			$("#w1_total_alkalinity").val(datarecord.total_alkalinity);
+			dataRecord.w1_total_alkalinity = datarecord.total_alkalinity;
+			$("#w1_ph").val(datarecord.ph);
+			dataRecord.w1_ph = datarecord.ph;
+			$("#w1_cost").val(datarecord.cost);
+			dataRecord.w1_cost = datarecord.cost;
+			calcWater();
+		}
+	});
+	$("#w1_amount").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w1_calcium").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w1_magnesium").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w1_sodium").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w1_total_alkalinity").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w1_chloride").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w1_sulfate").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w1_ph").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+
+	$("#w2_name").jqxDropDownList({
+		placeHolder: "Kies meng water:",
+		theme: theme,
+		source: waterlist,
+		displayMember: "name",
+		width: 250,
+		height: 27,
+		dropDownWidth: 400,
+		dropDownHeight: 400
+	});
+	$("#w2_name").on('select', function (event) {
+		if (event.args) {
+			var index = event.args.index;
+			var datarecord = waterlist.records[index];
+			dataRecord.w2_name = datarecord.name;
+			$("#w2_calcium").val(datarecord.calcium);
+			dataRecord.w2_calcium = datarecord.calcium;
+			$("#w2_sulfate").val(datarecord.sulfate);
+			dataRecord.w2_sulfate = datarecord.sulfate;
+			$("#w2_chloride").val(datarecord.chloride);
+			dataRecord.w2_chloride = datarecord.chloride;
+			$("#w2_sodium").val(datarecord.sodium);
+			dataRecord.w2_sodium = datarecord.sodium;
+			$("#w2_magnesium").val(datarecord.magnesium);
+			dataRecord.w2_magnesium = datarecord.magnesium;
+			$("#w2_total_alkalinity").val(datarecord.total_alkalinity);
+			dataRecord.w2_total_alkalinity = datarecord.total_alkalinity;
+			$("#w2_ph").val(datarecord.ph);
+			dataRecord.w2_ph = datarecord.ph;
+			$("#w2_cost").val(datarecord.cost);
+			dataRecord.w2_cost = datarecord.cost;
+			$("#w2_amount").jqxNumberInput({ max: 100000, readOnly: false }); // Set high max to enable the spinbuttons.
+			calcWater();
+		}
+	});
+	$("#w2_amount").jqxNumberInput({ inputMode: 'simple', spinMode: 'simple', theme: theme, width: 94, height: 23, min: 0, max: 0, decimalDigits: 1, spinButtons: true, spinButtonsStep: 0.5, readOnly: true });
+	$("#w2_calcium").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w2_magnesium").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w2_sodium").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w2_total_alkalinity").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w2_chloride").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w2_sulfate").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+	$("#w2_ph").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
+
+	$("#wg_amount").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
 	$("#wg_calcium").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
 	$("#wg_magnesium").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
 	$("#wg_sodium").jqxNumberInput({ inputMode: 'simple', theme: theme, width: 74, height: 23, decimalDigits: 1, readOnly: true });
@@ -1797,7 +1874,6 @@
 		var hoprow = $('#hopGrid').jqxGrid('getrows');
 		var miscrow = $('#miscGrid').jqxGrid('getrows');
 		var yeastrow = $('#yeastGrid').jqxGrid('getrows');
-		var waterrow = $('#waterGrid').jqxGrid('getrows');
 		var mashrow = $('#mashGrid').jqxGrid('getrows');
 		var row = {
 			record: my_record,
@@ -1839,15 +1915,34 @@
 			sparge_temp: parseFloat($("#sparge_temp").jqxNumberInput('decimal')),
 			sparge_ph: parseFloat($("#sparge_ph").jqxNumberInput('decimal')),
 			sparge_volume: parseFloat($("#sparge_volume").jqxNumberInput('decimal')),
-			sparge_acid_type: $("#sparge_acid_type").val(),
-			sparge_acid_perc: parseFloat($("#sparge_acid_perc").jqxNumberInput('decimal')),
-			sparge_acid_amount: parseFloat($("#sparge_acid_amount").jqxNumberInput('decimal')),
+		//	sparge_acid_type: $("#sparge_acid_type").val(),
+		//	sparge_acid_perc: parseFloat($("#sparge_acid_perc").jqxNumberInput('decimal')),
+		//	sparge_acid_amount: parseFloat($("#sparge_acid_amount").jqxNumberInput('decimal')),
 			calc_acid: $("#calc_acid").val(),
+			w1_name: $("#w1_name").val(),
+			w1_amount: parseFloat($("#w1_amount").jqxNumberInput('decimal')),
+			w1_calcium: parseFloat($("#w1_calcium").jqxNumberInput('decimal')),
+			w1_sulfate: parseFloat($("#w1_sulfate").jqxNumberInput('decimal')),
+			w1_chloride: parseFloat($("#w1_chloride").jqxNumberInput('decimal')),
+			w1_sodium: parseFloat($("#w1_sodium").jqxNumberInput('decimal')),
+			w1_magnesium: parseFloat($("#w1_magnesium").jqxNumberInput('decimal')),
+			w1_total_alkalinity: parseFloat($("#w1_total_alkalinity").jqxNumberInput('decimal')),
+			w1_ph: parseFloat($("#w1_ph").jqxNumberInput('decimal')),
+			w1_cost: dataRecord.w1_cost,
+			w2_name: $("#w2_name").val(),
+			w2_amount: parseFloat($("#w2_amount").jqxNumberInput('decimal')),
+			w2_calcium: parseFloat($("#w2_calcium").jqxNumberInput('decimal')),
+			w2_sulfate: parseFloat($("#w2_sulfate").jqxNumberInput('decimal')),
+			w2_chloride: parseFloat($("#w2_chloride").jqxNumberInput('decimal')),
+			w2_sodium: parseFloat($("#w2_sodium").jqxNumberInput('decimal')),
+			w2_magnesium: parseFloat($("#w2_magnesium").jqxNumberInput('decimal')),
+			w2_total_alkalinity: parseFloat($("#w2_total_alkalinity").jqxNumberInput('decimal')),
+			w2_ph: parseFloat($("#w2_ph").jqxNumberInput('decimal')),
+			w2_cost: dataRecord.w2_cost,
 			fermentables: fermentablerow,
 			hops: hoprow,
 			miscs: miscrow,
 			yeasts: yeastrow,
-			waters: waterrow,
 			mashs: mashrow
 		};
 		var data = "update=true&" + $.param(row);
--- a/www/rec_edit.php	Mon Dec 17 22:24:32 2018 +0100
+++ b/www/rec_edit.php	Wed Dec 19 21:58:21 2018 +0100
@@ -12,8 +12,8 @@
       <li>Hoppen</li>
       <li>Diversen</li>
       <li>Gist</li>
+      <li>Maischen</li>
       <li>Water</li>
-      <li>Maischen</li>
      </ul>
 
      <div> <!-- tab algemeen -->
@@ -160,6 +160,25 @@
       </div>
      </div> <!-- tab gisten -->
 
+     <div> <!-- tab maischen -->
+      <div style="overflow: hidden;">
+       <table style="width: 100%;">
+        <tr>
+         <td style="vertical-align: top; float: right; padding: 3px;">Maischchema:</td>
+         <td align="left" style="vertical-align: top; padding: 3px;"><input id="mash_name" /></td>
+         <td style="vertical-align: top; float: right; padding: 3px;">Maish pH:</td>
+         <td style="padding: 3px;"><div id="mash_ph"></div></td>
+         <td style="vertical-align: top; float: right; padding: 3px;">Spoelwater temp:</td>
+         <td style="padding: 3px;"><div id="sparge_temp"></div></td>
+        </tr>
+        <tr>
+         <td align="right" style="vertical-align: top; padding: 3px;">Stappen:</td>
+         <td align="left" colspan="5" style="padding: 3px;"><div id="mashGrid">Graat</div></td>
+        </tr>
+       </table>
+      </div>
+     </div> <!-- tab maischen -->
+
      <div> <!-- tab water -->
       <div style="overflow: hidden;">
        <table style="width: 100%;">
@@ -172,18 +191,14 @@
          <td style="padding: 3px;"><div id="tgt_mash_ph"></div></td>
         </tr>
         <tr>
-         <td align="right" style="vertical-align: top;">Water:</td>
-	 <td align="left" colspan="5"><div id="waterGrid"></div></td>
-	</tr>
-        <tr>
          <td></td>
          <td align="left" colspan="5">
           <div id='water_totals'>
  	   <table style="width: 100%;">
             <caption>Water overzicht</caption>
-    	    <tr>
-	     <td></td>
-             <td style="width: 77px; padding: 3px;">Volume</td>
+	    <tr>
+             <td align="left" style="vertical-align: top; padding: 3px;">Water profiel</td>
+             <td style="width: 97px; padding: 3px;">Volume</td>
              <td style="width: 77px; padding: 3px;">Ca</td>
              <td style="width: 77px; padding: 3px;">Mg</td>
              <td style="width: 77px; padding: 3px;">Na</td>
@@ -191,10 +206,32 @@
              <td style="width: 77px; padding: 3px;">Cl</td>
 	     <td style="width: 77px; padding: 3px;">SO4</td>
              <td style="width: 77px; padding: 3px;">pH</td>
- 	    </tr>
+	    </tr>
+	    <tr>
+             <td><div id="w1_name"></div></td>
+             <td><div id="w1_amount"></div></td>
+             <td><div id="w1_calcium"></div></td>
+             <td><div id="w1_magnesium"></div></td>
+             <td><div id="w1_sodium"></div></td>
+             <td><div id="w1_total_alkalinity"></div></td>
+             <td><div id="w1_chloride"></div></td>
+             <td><div id="w1_sulfate"></div></td>
+             <td><div id="w1_ph"></div></td>
+            </tr>
+	    <tr>
+             <td><div id="w2_name"></div></td>
+             <td><div id="w2_amount"></div></td>
+             <td><div id="w2_calcium"></div></td>
+             <td><div id="w2_magnesium"></div></td>
+             <td><div id="w2_sodium"></div></td>
+             <td><div id="w2_total_alkalinity"></div></td>
+             <td><div id="w2_chloride"></div></td>
+             <td><div id="w2_sulfate"></div></td>
+             <td><div id="w2_ph"></div></td>
+            </tr>
             <tr>
 	     <td style="vertical-align: top; padding: 3px; float: left;">Gemengd water:</td>
-             <td><div id="wg_volume"></div></td>
+             <td><div id="wg_amount"></div></td>
              <td><div id="wg_calcium"></div></td>
              <td><div id="wg_magnesium"></div></td>
              <td><div id="wg_sodium"></div></td>
@@ -215,6 +252,17 @@
              <td><div id="wb_ph"></div></td>
 	    </tr>
             <tr>
+             <td style="vertical-align: top; padding: 3px; float: left;">Resultaat:</td>
+             <td><div></div></td>
+             <td><div id="wr_calcium"></div></td>
+             <td><div id="wr_magnesium"></div></td>
+             <td><div id="wr_sodium"></div></td>
+             <td><div id="wr_total_alkalinity"></div></td>
+             <td><div id="wr_chloride"></div></td>
+             <td><div id="wr_sulfate"></div></td>
+             <td><div id="wr_ph"></div></td>
+            </tr>
+            <tr>
              <td style="vertical-align: top; padding: 3px; float: left;">Doel waterprofiel:</td>
              <td><div></div></td>
              <td><div id="pr_calcium"></div></td>
@@ -269,25 +317,6 @@
       </div>
      </div> <!-- tab water -->
 
-     <div> <!-- tab maischen -->
-      <div style="overflow: hidden;">
-       <table style="width: 100%;">
-	<tr>
-         <td style="vertical-align: top; float: right; padding: 3px;">Maischchema:</td>
-	 <td align="left" style="vertical-align: top; padding: 3px;"><input id="mash_name" /></td>
-         <td style="vertical-align: top; float: right; padding: 3px;">Maish pH:</td>
-	 <td style="padding: 3px;"><div id="mash_ph"></div></td>
-         <td style="vertical-align: top; float: right; padding: 3px;">Spoelwater temp:</td>
-         <td style="padding: 3px;"><div id="mash_sparge_temp"></div></td>
-        </tr>
-        <tr>
-         <td align="right" style="vertical-align: top; padding: 3px;">Stappen:</td>
-         <td align="left" colspan="5" style="padding: 3px;"><div id="mashGrid">Graat</div></td>
-        </tr>
-       </table>
-      </div>
-     </div> <!-- tab maischen -->
-
    </div> <!-- jqxTabs -->
 
 <?php

mercurial