Go to main content

Textpattern CMS support forum

You are not logged in. Register | Login | Help

#91 2012-07-01 21:16:36

Gocom
Developer Emeritus
From: Helsinki, Finland
Registered: 2006-07-14
Posts: 4,533
Website

Re: New sections tab, multi-edit control block

Btw, the categories panel is broken.

The IDs are used to link the .multi-option blocks to the edit_method options. The IDs are named after the values. Since they don’t match, the categories panel doesn’t work.

These changes would require that the scripts functionality is changed too in some form. Which is why I was suggesting the random ID thing. Since you have an random ID consistently present, the ID can be broken apart correctly.

Offline

#92 2012-07-01 21:18:17

Bloke
Developer
From: Leeds, UK
Registered: 2006-01-29
Posts: 12,501
Website GitHub

Re: New sections tab, multi-edit control block

Gocom wrote:

Btw, the categories panel is broken.

Yikes. OK than. Code suggestions?


The smd plugin menagerie — for when you need one more gribble of power from Textpattern. Bleeding-edge code available on GitHub.

Hire Txp Builders – finely-crafted code, design and Txp

Offline

#93 2012-07-01 21:29:51

Gocom
Developer Emeritus
From: Helsinki, Finland
Registered: 2006-07-14
Posts: 4,533
Website

Re: New sections tab, multi-edit control block

I will send a patch soon. It will contain some other optimizations too to the multi-edit jQuery plugin. Wait for half an hour or so.

Offline

#94 2012-07-01 21:30:46

Bloke
Developer
From: Leeds, UK
Registered: 2006-01-29
Posts: 12,501
Website GitHub

Re: New sections tab, multi-edit control block

Gocom wrote:

I will send a patch soon. It will contain some other optimizations too to the multi-edit jQuery plugin. Wait for half an hour or so.

Legend, thanks.


The smd plugin menagerie — for when you need one more gribble of power from Textpattern. Bleeding-edge code available on GitHub.

Hire Txp Builders – finely-crafted code, design and Txp

Offline

#95 2012-07-01 22:48:20

Gocom
Developer Emeritus
From: Helsinki, Finland
Registered: 2006-07-14
Posts: 4,533
Website

Re: New sections tab, multi-edit control block

Stef, please take a look:

Index: textpattern.js
===================================================================
--- textpattern.js	(revision 3886)
+++ textpattern.js	(working copy)
@@ -143,13 +143,13 @@
 /**
  * Multi-edit functions
  * @param string|obj method
- * @param obj options
+ * @param obj opt
  * @since 4.5.0
  */

-jQuery.fn.txpMultiEditForm = function(method, options)
+jQuery.fn.txpMultiEditForm = function(method, opt)
 {
-	var args = {}, opt;
+	var args = {};

 	var defaults = {
 		'checkbox' : 'input[name="selected[]"][type=checkbox]',
@@ -166,26 +166,23 @@

 	if ($.type(method) !== 'string')
 	{
-		options = method;
+		opt = method;
 		method = null;
 	}
 	else
 	{
-		args = options;
+		args = opt;
 	}

-	opt = options;
-
 	this.closest('form').each(function() {

 		var $this = $(this), form = {}, public = {}, private = {};
-		
+
 		if ($this.data('_txpMultiEdit'))
 		{
 			form = $this.data('_txpMultiEdit');
 			opt = $.extend(form.opt, opt);
 		}
-		
 		else
 		{
 			opt = $.extend(defaults, opt);
@@ -212,6 +209,11 @@
 				'value' : null,
 				'html' : null
 			}, options);
+			
+			if (!settings.value)
+			{
+				return public;
+			}

 			var option = form.editMethod.find('option').filter(function() {
 				return $(this).attr('value') === settings.value;
@@ -247,7 +249,7 @@

 			return public;
 		};
-		
+
 		/**
 		 * Selects rows based on supplied arguments. Only one of the filters applies at time.
 		 * @param array index Select based on row's index.
@@ -255,7 +257,7 @@
 		 * @param array value [value1, value2, value3, ...]
 		 * @param bool checked Set matched checked or unchecked. FALSE to uncheck.
 		 */
-		
+
 		public.select = function(options)
 		{
 			var settings = $.extend({
@@ -264,58 +266,58 @@
 				'value' : null,
 				'checked' : true
 			}, options);
-			
+
 			var obj = $this.find(form.pattern);
-			
+
 			if (settings.value !== null)
 			{
 				obj = obj.filter(function() {
 					return $.inArray($(this).attr('value'), settings.value) !== -1;
 				});
 			}
-			
+
 			else if (settings.index !== null)
 			{
 				obj = obj.filter(function(index) {
 					return $.inArray(index, settings.index) !== -1;
 				});
 			}
-			
+
 			else if (settings.range !== null)
 			{
 				obj = obj.slice(settings.range[0], settings.range[1]);
 			}
-		
+
 			obj.prop('checked', settings.checked).change();
 			return public;
 		};
-		
+
 		/**
 		 * Binds checkboxes
 		 */
-		
+
 		private.bindRows = function()
 		{
 			form.rows = $this.find(opt.row);
 			form.boxes = $this.find(form.pattern);
 			return private;
 		};
-		
+
 		/**
 		 * Highlights selected rows
 		 */
-		
+
 		private.highlight = function()
 		{
 			form.boxes.filter(':checked').closest(opt.highlighted).addClass(opt.selectedClass);
 			form.boxes.filter(':not(:checked)').closest(opt.highlighted).removeClass(opt.selectedClass);
 			return private;
 		};
-		
+
 		/**
 		 * Extends click region to whole row
 		 */
-		
+
 		private.extendedClick = function()
 		{
 			if (opt.rowClick)
@@ -328,9 +330,9 @@
 			}

 			obj.live('click', function(e) {
-			
+
 				var self = ($(e.target).is(form.pattern) || $(this).is(form.pattern));
-	
+
 				if (!self && (e.target != this || $(this).is('a, :input') || $(e.target).is('a, :input')))
 				{
 					return;
@@ -347,72 +349,53 @@
 				{
 					return;
 				}
-				
+
 				private.bindRows();
-				
+
 				var checked = box.prop('checked');
-					
+
 				if (self)
 				{
 					checked = !checked;
 				}
-					
-				if (form.lastCheck)
+
+				if (e.shiftKey && form.lastCheck)
 				{
+					var start = form.boxes.index(box);
 					var end = form.boxes.index(form.lastCheck);
+
+					public.select({
+						'range' : [Math.min(start, end), Math.max(start, end)+1],
+						'checked' : !checked
+					});
 				}
-					
+				else if (!self)
+				{
+					box.prop('checked', !checked).change();
+				}
+
 				if (checked === false)
 				{
-					if (e.shiftKey && form.lastCheck)
-					{
-						var start = form.boxes.index(box);
-						
-						public.select({
-							'range' : [Math.min(start, end), Math.max(start, end)+1]
-						});
-					}
-					
-					else if (!self)
-					{
-						box.prop('checked', true).change();
-					}
-					
 					form.lastCheck = box;
 				}
-				
 				else
 				{
-					if (e.shiftKey && form.lastCheck)
-					{
-						var start = form.boxes.index(box);
-						
-						public.select({
-							'range' : [Math.min(start, end), Math.max(start, end)+1],
-							'checked' : false
-						});
-					}
-					else if (!self)
-					{
-						box.prop('checked', false).change();
-					}
-				
 					form.lastCheck = null;
 				}
 			});
-			
+
 			return private;
 		};
-		
+
 		/**
 		 * Tracks row checks
 		 */
-		
+
 		private.checked = function()
 		{
 			form.boxes.live('change', function(e) {
 				var box = $(this);
-				
+
 				if (box.prop('checked'))
 				{
 					$(this).closest(opt.highlighted).addClass(opt.selectedClass);
@@ -424,14 +407,14 @@
 					form.selectAll.prop('checked', false);
 				}
 			});
-			
+
 			return private;
 		};
-		
+
 		/**
 		 * Handles edit method selecting
 		 */
-		
+
 		private.changeMethod = function()
 		{
 			form.button.hide();
@@ -482,14 +465,29 @@
 		{
 			private.bindRows().highlight().extendedClick().checked().changeMethod().sendForm();

-			$this.find('.multi-option:not(.multi-step)').each(function() {
-				public.addOption({
-					'label' : null,
-					'html' : $(this).contents(),
-					'value' : $(this).attr('id').substring(13)
+			(function() {
+				var multiOptions = $this.find('.multi-option:not(.multi-step)');
+
+				form.editMethod.find('option[value!=""]').each(function() {
+					var value = $(this).val();
+
+					var option = multiOptions.filter(function() {
+						return $(this).hasClass('multi-option-'+value);
+					});
+
+					if (option.length > 0)
+					{
+						public.addOption({
+							'label' : null,
+							'html' : option.eq(0).contents(),
+							'value' : $(this).val()
+						});
+					}
 				});
-			}).remove();

+				multiOptions.remove();
+			})();
+
 			form.selectAll.live('change', function(e) {
 				public.select({
 					'checked' : $(this).prop('checked')
Index: lib/txplib_html.php
===================================================================
--- lib/txplib_html.php	(revision 3886)
+++ lib/txplib_html.php	(working copy)
@@ -876,11 +876,10 @@
  * @param  string  $dir Sorting direction
  * @param  string  $crit Search criterion
  * @param  string  $search_method Search method
- * @param  string  $id_suffix Added to the HTML id attribute; useful if more than one similar control placed per page
  * @return string  HTML
  */

-	function multi_edit($options, $event=null, $step=null, $page='', $sort='', $dir='', $crit='', $search_method='', $id_suffix='')
+	function multi_edit($options, $event=null, $step=null, $page='', $sort='', $dir='', $crit='', $search_method='')
 	{
 		$html = $methods = array();
 		$methods[''] = gTxt('with_selected_option');
@@ -905,8 +904,7 @@

 				if (isset($option['html']))
 				{
-					$html[$value] = '<div class="multi-option" id="multi-option-'.
-						txpspecialchars($value).($id_suffix ? '-'.txpspecialchars($id_suffix) : '').'">'.$option['html'].'</div>';
+					$html[$value] = '<div class="multi-option multi-option-'.txpspecialchars($value).'">'.$option['html'].'</div>';
 				}
 			}
 			else

It basically changes the thing to work with classes instead of IDs. This solves all the collisions issues. Instead of the JavaScript picking .multi-options it uses the actual <option> elements to trace the steps from markup. When 4.6 and HTML5 lands, those classes could be changed to data- attributes even simplifying the logic even more.

Other changes are some basic cleanup and small fixes. Main thing is that it now prevents hooking with addOption() method to the default empty option (by accident) as that would just cause a loop of confirmation dialogs if anything. It also merges two almost identical condition blocks used for shift+click. Just reverses the booleans in props and likes, leading to much shorter code in that scenario.

Last edited by Gocom (2012-07-01 22:49:23)

Offline

#96 2012-07-01 22:55:47

Gocom
Developer Emeritus
From: Helsinki, Finland
Registered: 2006-07-14
Posts: 4,533
Website

Re: New sections tab, multi-edit control block

If you are wondering why the diff is as big as it is, is because I removed my auto-indents. In Textpattern’s source empty lines aren’t leveled, so I decided to remove those extra indentations to match the general styling.

Last edited by Gocom (2012-07-01 22:57:23)

Offline

#97 2012-07-01 23:15:32

Bloke
Developer
From: Leeds, UK
Registered: 2006-01-29
Posts: 12,501
Website GitHub

Re: New sections tab, multi-edit control block

Works like a dream. Awesome work, as always sir. I missed the nightly build window by 11 minutes because I was playing with it for too long and admiring your code :-)


The smd plugin menagerie — for when you need one more gribble of power from Textpattern. Bleeding-edge code available on GitHub.

Hire Txp Builders – finely-crafted code, design and Txp

Offline

Board footer

Powered by FluxBB