fix: Multiple rows for same warehouse and batches in pick list (#33456)

diff --git a/erpnext/stock/doctype/pick_list/pick_list.js b/erpnext/stock/doctype/pick_list/pick_list.js
index 799406c..8213adb 100644
--- a/erpnext/stock/doctype/pick_list/pick_list.js
+++ b/erpnext/stock/doctype/pick_list/pick_list.js
@@ -51,7 +51,15 @@
 		if (!(frm.doc.locations && frm.doc.locations.length)) {
 			frappe.msgprint(__('Add items in the Item Locations table'));
 		} else {
-			frm.call('set_item_locations', {save: save});
+			frappe.call({
+				method: "set_item_locations",
+				doc: frm.doc,
+				args: {
+					"save": save,
+				},
+				freeze: 1,
+				freeze_message: __("Setting Item Locations..."),
+			});
 		}
 	},
 	get_item_locations: (frm) => {
diff --git a/erpnext/stock/doctype/pick_list/pick_list.py b/erpnext/stock/doctype/pick_list/pick_list.py
index 8704b67..953fca7 100644
--- a/erpnext/stock/doctype/pick_list/pick_list.py
+++ b/erpnext/stock/doctype/pick_list/pick_list.py
@@ -135,6 +135,7 @@
 
 		# reset
 		self.delete_key("locations")
+		updated_locations = frappe._dict()
 		for item_doc in items:
 			item_code = item_doc.item_code
 
@@ -155,7 +156,26 @@
 			for row in locations:
 				location = item_doc.as_dict()
 				location.update(row)
-				self.append("locations", location)
+				key = (
+					location.item_code,
+					location.warehouse,
+					location.uom,
+					location.batch_no,
+					location.serial_no,
+					location.sales_order_item or location.material_request_item,
+				)
+
+				if key not in updated_locations:
+					updated_locations.setdefault(key, location)
+				else:
+					updated_locations[key].qty += location.qty
+					updated_locations[key].stock_qty += location.stock_qty
+
+		for location in updated_locations.values():
+			if location.picked_qty > location.stock_qty:
+				location.picked_qty = location.stock_qty
+
+			self.append("locations", location)
 
 		# If table is empty on update after submit, set stock_qty, picked_qty to 0 so that indicator is red
 		# and give feedback to the user. This is to avoid empty Pick Lists.