Index: editor.js
===================================================================
--- editor.js	(revision 546)
+++ editor.js	(working copy)
@@ -4,6 +4,11 @@
 		$gp.init();
 		$gp.editor.table = table;
 		$gp.editor.install_hooks();
+
+		if (window.sessionStorage && sessionStorage.gp_select_row) {
+			$gp.editor.show($('a.edit' + sessionStorage.gp_select_row, table));
+			sessionStorage.gp_select_row = '';
+		}
 	},
 	original_id_from_row_id: function(row_id) {
 		return row_id.split('-')[0];
@@ -26,14 +31,37 @@
 		$('tr:first', $gp.editor.table).hide();
 		$('textarea:first', editor).focus();
 	},
+	prev: function() {
+		if (!$gp.editor.current) return;
+		var prev = $gp.editor.current.prevAll('tr.editor');
+		if (prev.length) {
+			$gp.editor.show(prev.eq(0));
+		} else {
+			if ($('.paging .previous').hasClass('disabled')) {
+				$gp.editor.hide();
+			} else {
+				if (window.sessionStorage)
+					sessionStorage.gp_select_row = ':last';
+
+				location.href = $('.paging .previous').attr('href');
+			}
+		}
+	},
 	next: function() {
 		if (!$gp.editor.current) return;
-		//TODO: go to next page if needed
 		var next = $gp.editor.current.nextAll('tr.editor');
-		if (next.length)
+		if (next.length) {
 			$gp.editor.show(next.eq(0));
-		else
-			$gp.editor.hide();
+		} else {
+			if ($('.paging .next').hasClass('disabled')) {
+				$gp.editor.hide();
+			} else {
+				if (window.sessionStorage)
+					sessionStorage.gp_select_row = ':first';
+
+				location.href = $('.paging .next').attr('href');
+			}
+		}
 	},
 	hide: function(editor) {
 		editor = editor? editor : $gp.editor.current;
@@ -54,7 +82,25 @@
 		$('button.ok', 'tr.editor').live('click', $gp.editor.hooks.ok);
 		$('tr.preview', $gp.editor.table).live('dblclick', $gp.editor.hooks.show);
 		$('select.priority', $gp.editor.table).live('change', $gp.editor.hooks.set_priority);
+		$('textarea', 'tr.editor').live('keydown', $gp.editor.hooks.keydown);
 	},
+	keydown: function(e) {
+		if (e.keyCode == 27)
+			$gp.editor.hide();
+		else if (e.keyCode == 33)
+			$gp.editor.prev();
+		else if (e.keyCode == 34)
+			$gp.editor.next();
+		else if (e.keyCode == 13 && e.shiftKey) {
+			var target = $(e.target);
+			if (target.nextAll('textarea').length)
+				target.nextAll('textarea').eq(0).focus()
+			else
+				$gp.editor.save(target.parents('tr.editor').find('button.ok'));
+		} else
+			return true;
+		return false;
+	},
 	replace_current: function(html) {
 		if (!$gp.editor.current) return;
 		$gp.editor.current.after(html);
@@ -75,7 +121,7 @@
 		}).get().join('&');
 		$.ajax({type: "POST", url: $gp_editor_options.url, data: data, dataType: 'json',
 			success: function(data){
-				button.attr('disabled', '');
+				button.removeAttr('disabled');
 				$gp.notices.success('Saved!');
 				for(original_id in data) {
 					$gp.editor.replace_current(data[original_id]);
@@ -87,7 +133,7 @@
 				}
 			},
 			error: function(xhr, msg, error) {
-				button.attr('disabled', '');
+				button.removeAttr('disabled');
 				msg = xhr.responseText? 'Error: '+ xhr.responseText : 'Error saving the translation!';
 				$gp.notices.error(msg);
 			}
@@ -101,7 +147,7 @@
 		data = {priority: $('option:selected', select).attr('value')};
 		$.ajax({type: "POST", url: $gp_editor_options.set_priority_url.replace('%original-id%', editor.original_id), data: data,
 			success: function(data){
-				select.attr('disabled', '');
+				select.removeAttr('disabled');
 				$gp.notices.success('Priority set!');
 				var new_priority_class = 'priority-'+$('option:selected', select).text();
 				$gp.editor.current.addClass(new_priority_class);
@@ -118,11 +164,11 @@
 		if (!$gp.editor.current || !$gp.editor.current.translation_id) return;
 		var editor = $gp.editor.current;
 		button.attr('disabled', 'disabled');		
-		$gp.notices.notice('Setting status to &#8220;'+status+'&#8222;&hellip;');
+		$gp.notices.notice('Setting status to &#8220;'+status+'&#8221;&hellip;');
 		var data = {translation_id: editor.translation_id, status: status};
 		$.ajax({type: "POST", url: $gp_editor_options.set_status_url, data: data,
 			success: function(data){
-				button.attr('disabled', '');
+				button.removeAttr('disabled');
 				$gp.notices.success('Status set!');
 				$gp.editor.replace_current(data);
 			},
@@ -130,7 +176,7 @@
 				msg = xhr.responseText? 'Error: '+ xhr.responseText : 'Error setting the status!';
 				$gp.notices.error(msg);
 			}
-		});		
+		});
 	},
 	discard_warning: function(link) {
 		if (!$gp.editor.current) return;
@@ -196,6 +242,9 @@
 			$gp.editor.save($(this));
 			return false;
 		},
+		keydown: function(e) {
+			return $gp.editor.keydown(e);
+		},
 		copy: function() {
 			$gp.editor.copy($(this));
 			return false;

