Ver código fonte

HUE-715 Full rows are clickable across Hue
(cherry picked from commit 040ddf40e9cf64a271ed853ab35344077fce92e2)

Introduced jHueRowSelector
Removed jHueContextMenu

On top of cherry-pick (romain): fixed selector bug and reference to
old contextmenu test bug

Enrico Berti 13 anos atrás
pai
commit
f06352a

+ 25 - 16
apps/beeswax/src/beeswax/templates/list_designs.mako

@@ -46,9 +46,9 @@ ${layout.menubar(section='saved queries')}
         <td>
           % if may_edit:
             % if design.type == models.SavedQuery.REPORT:
-              <a href="${ url('beeswax.views.edit_report', design_id=design.id) }">${design.name}</a>
+              <a href="${ url('beeswax.views.edit_report', design_id=design.id) }" data-row-selector="true">${design.name}</a>
             % else:
-              <a href="${ url('beeswax.views.execute_query', design_id=design.id) }">${design.name}</a>
+              <a href="${ url('beeswax.views.execute_query', design_id=design.id) }" data-row-selector="true">${design.name}</a>
             % endif
           % else:
             ${design.name}
@@ -71,20 +71,28 @@ ${layout.menubar(section='saved queries')}
           ${ timesince(design.mtime) } ago
         </td>
         <td>
-			<a class="btn small contextEnabler" data-menuid="${design.id}">Options</a>
-			<ul class="contextMenu" id="menu${design.id}">
-	      	% if may_edit:
-	             % if design.type == models.SavedQuery.REPORT:
-	               <li><a href="${ url('beeswax.views.edit_report', design_id=design.id) }" title="Edit this report." class="contextItem">Edit</a></li>
-	             % else:
-	               <li><a href="${ url('beeswax.views.execute_query', design_id=design.id) }" title="Edit this query." class="contextItem">Edit</a></li>
-	             % endif
-	             <li><a href="javascript:void(0)" data-confirmation-url="${ url('beeswax.views.delete_design', design_id=design.id) }" title="Delete this query." class="contextItem confirmationModal">Delete</a></li>
-	             <li><a href="${ url('beeswax.views.list_query_history') }?design_id=${design.id}" title="View the usage history of this query." class="contextItem">Usage History</a></li>
+			<div class="btn-group">
+				<a href="#" data-toggle="dropdown" class="btn dropdown-toggle">
+					Options
+		    		<span class="caret"></span>
+		    	</a>
+				<ul class="dropdown-menu">
+
+					% if may_edit:
+			             % if design.type == models.SavedQuery.REPORT:
+			               <li><a href="${ url('beeswax.views.edit_report', design_id=design.id) }" title="Edit this report." class="contextItem">Edit</a></li>
+			             % else:
+			               <li><a href="${ url('beeswax.views.execute_query', design_id=design.id) }" title="Edit this query." class="contextItem">Edit</a></li>
+			             % endif
+			             <li><a href="javascript:void(0)" data-confirmation-url="${ url('beeswax.views.delete_design', design_id=design.id) }" title="Delete this query." class="contextItem confirmationModal">Delete</a></li>
+			             <li><a href="${ url('beeswax.views.list_query_history') }?design_id=${design.id}" title="View the usage history of this query." class="contextItem">Usage History</a></li>
+
+			        % endif
+						<li><a href="${ url('beeswax.views.clone_design', design_id=design.id) }" title="Copy this query." class="contextItem">Clone</a></li>
+		    	</ul>
+		    </div>
+
 
-	        % endif
-				<li><a href="${ url('beeswax.views.clone_design', design_id=design.id) }" title="Copy this query." class="contextItem">Clone</a></li>
-			</ul>
         </td>
       </tr>
     % endfor
@@ -123,7 +131,6 @@ ${comps.pagination(page)}
 				{ "bSortable": false }
 			]
 		});
-		$(".contextEnabler").jHueContextMenu();
 
 		$(".confirmationModal").live("click", function(){
 			$.getJSON($(this).attr("data-confirmation-url"), function(data){
@@ -132,6 +139,8 @@ ${comps.pagination(page)}
 			});
 			$("#deleteQuery").modal("show");
 		});
+
+		$("a[data-row-selector='true']").jHueRowSelector();
 	});
 </script>
 

+ 2 - 2
apps/beeswax/src/beeswax/templates/list_history.mako

@@ -127,7 +127,7 @@ ${layout.menubar(section='history')}
 		        <td>${models.QueryHistory.STATE[query.last_state]}</td>
 		        <td>
 		          % if qcontext and query.last_state != models.QueryHistory.STATE.expired.index:
-		            <a href="${ url('beeswax.views.watch_query', id=query.id) }?context=${qcontext|u}">Results</a>
+		            <a href="${ url('beeswax.views.watch_query', id=query.id) }?context=${qcontext|u}" data-row-selector="true">Results</a>
 		          % else:
 		            ~
 		          % endif
@@ -152,7 +152,7 @@ ${layout.menubar(section='history')}
 			"bFilter": false
 		});
 
-
+		$("a[data-row-selector='true']").jHueRowSelector();
 
 	});
 </script>

+ 34 - 19
apps/beeswax/src/beeswax/templates/my_queries.mako

@@ -22,7 +22,11 @@ from desktop.views import commonheader, commonfooter
 <%!  from beeswax.views import collapse_whitespace %>
 ${commonheader("Beeswax: My Queries", "beeswax", "100px")}
 ${layout.menubar(section='my queries')}
-
+<style>
+	.tab-content {
+		overflow:visible!important;
+	}
+</style>
 <div class="container-fluid">
 	<h1>Beeswax: My Queries</h1>
 
@@ -53,9 +57,9 @@ ${layout.menubar(section='my queries')}
 			            <tr>
 			              <td>
 			                % if design.type == models.SavedQuery.REPORT:
-			                  <a href="${ url('beeswax.views.edit_report', design_id=design.id) }">${design.name}</a>
+			                  <a href="${ url('beeswax.views.edit_report', design_id=design.id) }" data-row-selector="true">${design.name}</a>
 			                % else:
-			                  <a href="${ url('beeswax.views.execute_query', design_id=design.id) }">${design.name}</a>
+			                  <a href="${ url('beeswax.views.execute_query', design_id=design.id) }" data-row-selector="true">${design.name}</a>
 			                % endif
 			              </td>
 			              <td>
@@ -74,17 +78,22 @@ ${layout.menubar(section='my queries')}
 			                ${ timesince(design.mtime) } ago
 			              </td>
 			              <td>
-							<a class="btn small contextEnabler" data-menuid="${design.id}">Options</a>
-							<ul class="contextMenu" id="menu${design.id}">
-					             % if design.type == models.SavedQuery.REPORT:
-				                    <li><a href="${ url('beeswax.views.edit_report', design_id=design.id) }" title="Edit this report." class="contextItem">Edit</a></li>
-				                  % else:
-				                    <li><a href="${ url('beeswax.views.execute_query', design_id=design.id) }" title="Edit this query." class="contextItem">Edit</a></li>
-				                  % endif
-				                  <li><a href="javascript:void(0)" data-confirmation-url="${ url('beeswax.views.delete_design', design_id=design.id) }" title="Delete this query." class="contextItem confirmationModal">Delete</a></li>
-				                  <li><a href="${ url('beeswax.views.list_query_history') }?design_id=${design.id}" title="View the usage history of this query." class="contextItem">Usage History</a></li>
-				                  <li><a href="${ url('beeswax.views.clone_design', design_id=design.id) }" title="Copy this query." class="contextItem">Clone</a></li>
-							</ul>
+							<div class="btn-group">
+								<a href="#" data-toggle="dropdown" class="btn dropdown-toggle">
+									Options
+						    		<span class="caret"></span>
+						    	</a>
+								<ul class="dropdown-menu">
+									% if design.type == models.SavedQuery.REPORT:
+					                    <li><a href="${ url('beeswax.views.edit_report', design_id=design.id) }" title="Edit this report." class="contextItem">Edit</a></li>
+					                  % else:
+					                    <li><a href="${ url('beeswax.views.execute_query', design_id=design.id) }" title="Edit this query." class="contextItem">Edit</a></li>
+					                  % endif
+					                  <li><a href="javascript:void(0)" data-confirmation-url="${ url('beeswax.views.delete_design', design_id=design.id) }" title="Delete this query." class="contextItem confirmationModal">Delete</a></li>
+					                  <li><a href="${ url('beeswax.views.list_query_history') }?design_id=${design.id}" title="View the usage history of this query." class="contextItem">Usage History</a></li>
+					                  <li><a href="${ url('beeswax.views.clone_design', design_id=design.id) }" title="Copy this query." class="contextItem">Clone</a></li>
+						    	</ul>
+						    </div>
 			              </td>
 			            </tr>
 			          % endfor
@@ -122,7 +131,7 @@ ${layout.menubar(section='my queries')}
 		            <tr >
 		              <td>${query.submission_date.strftime("%x %X")}</td>
 		              ## TODO (bc): Only showing HQL (not REPORT)
-		              <td><a href="${ url('beeswax.views.execute_query', design_id=design.id) }" >${design.name}</a></td>
+		              <td><a href="${ url('beeswax.views.execute_query', design_id=design.id) }" data-row-selector="true">${design.name}</a></td>
 		              <td>
 		                <p>
 		                  % if len(query.query) > 100:
@@ -171,12 +180,16 @@ ${layout.menubar(section='my queries')}
 			"bPaginate": false,
 		    "bLengthChange": false,
 			"bInfo": false,
-			"bFilter": false
+			"bFilter": false,
+			"aoColumns": [
+				null,
+				null,
+				null,
+				null,
+				{ "bSortable": false }
+			]
 		});
 
-
-		$(".contextEnabler").jHueContextMenu();
-
 		$(".confirmationModal").live("click", function(){
 			$.getJSON($(this).attr("data-confirmation-url"), function(data){
 				$("#deleteQueryForm").attr("action", data.url);
@@ -185,6 +198,8 @@ ${layout.menubar(section='my queries')}
 			$("#deleteQuery").modal("show");
 		});
 
+		$("a[data-row-selector='true']").jHueRowSelector();
+
 	});
 </script>
 

+ 5 - 2
apps/beeswax/src/beeswax/templates/show_tables.mako

@@ -47,7 +47,7 @@ ${layout.menubar(section='tables')}
 				% for table in tables:
 					<tr>
 						<td>
-							<a href="${ url("beeswax.views.describe_table", table=table) }">${ table }</a>
+							<a href="${ url("beeswax.views.describe_table", table=table) }" data-row-selector="true">${ table }</a>
 						</td>
 						<td><a href="${ url("beeswax.views.read_table", table=table) }" class="btn">Browse Data</a></td>
 					</tr>
@@ -87,9 +87,12 @@ ${layout.menubar(section='tables')}
 			"bFilter": false,
 			"aoColumns": [
 				null,
-				{ "sWidth": "130px" },
+				{ "sWidth": "130px", "bSortable" : false },
 			 ]
 		});
+
+		$("a[data-row-selector='true']").jHueRowSelector();
+
 		% if not examples_installed:
 		$.getJSON("${ url('beeswax.views.install_examples') }",function(data){
 			$("#installSamplesMessage").text(data.title);

+ 0 - 1
apps/beeswax/src/beeswax/tests.py

@@ -208,7 +208,6 @@ for x in sys.stdin:
       SELECT * FROM test
     """
     response = _make_query(self.client, QUERY, name='select star', local=False)
-    assert_equal(2, len(response.context["download_urls"]))
     response = wait_for_query_to_finish(self.client, response)
     assert_equal(str(response.context['query_context'][0]), 'design')
     assert_true("<td>99</td>" in response.content)

+ 19 - 3
apps/filebrowser/src/filebrowser/templates/listdir_components.mako

@@ -84,7 +84,7 @@ from django.utils.encoding import smart_str
 			<% path = file['path'] %>
 			<tr class="file-row" data-search="${display_name}">
 				<td>
-					<h5><a href="${url('filebrowser.views.'+view, path=urlencode(path))}?file_filter=${file_filter}">${display_name}</a></h5>
+					<h5><a href="${url('filebrowser.views.'+view, path=urlencode(path))}?file_filter=${file_filter}" data-row-selector="true">${display_name}</a></h5>
 				</td>
 				<td>
 					% if "dir" == file['type']:
@@ -328,7 +328,6 @@ from django.utils.encoding import smart_str
 
         $("#filterInput").keyup(function() {
             oTable.fnFilter($(this).val(), 0 /* Column Idx */);
-            $(".contextEnabler").jHueContextMenu();
         });
 
         //delete handlers
@@ -424,7 +423,24 @@ from django.utils.encoding import smart_str
             $("#newDirectoryNameInput").removeClass("fieldError");
             $("#directoryNameRequiredAlert").hide();
         });
-	});
+
+        $(".pathChooser").click(function(){
+            var self = this;
+            $("#fileChooserRename").jHueFileChooser({
+                onFileChoose: function(filePath) {
+                    $(self).val(filePath);
+                },
+                onFolderChange: function(folderPath){
+                    $(self).val(folderPath);
+                },
+                createFolder: false,
+                uploadFile: false
+            });
+            $("#fileChooserRename").slideDown();
+        });
+
+        $("a[data-row-selector='true']").jHueRowSelector();
+    });
 </script>
 
 </%def>

+ 2 - 1
apps/jobbrowser/src/jobbrowser/templates/jobs.mako

@@ -89,7 +89,7 @@ ${commonheader("Job Browser", "jobbrowser")}
 			<td>${job.durationFormatted}</td>
 			<td>${job.startTimeFormatted}</td>
             <td>
-                <a href="${url('jobbrowser.views.single_job', jobid=job.jobId)}" title="View this job">View</a>
+                <a href="${url('jobbrowser.views.single_job', jobid=job.jobId)}" title="View this job" data-row-selector="true">View</a>
                 % if job.status.lower() == 'running' or job.status.lower() == 'pending':
                 % if request.user.is_superuser or request.user.username == job.user:
                 - <a href="#" title="Kill this job" onclick="$('#kill-job').submit()">Kill</a>
@@ -139,6 +139,7 @@ ${commonheader("Job Browser", "jobbrowser")}
 			{"bSortable":false}
 			]
 		});
+		$("a[data-row-selector='true']").jHueRowSelector();
 	});
 	</script>
 

+ 2 - 1
apps/jobbrowser/src/jobbrowser/templates/tasks.mako

@@ -90,7 +90,7 @@
 					<td>${t.mostRecentState}</td>
 					<td>${t.execStartTimeFormatted}</td>
 					<td>${t.execFinishTimeFormatted}</td>
-					<td><a href="/jobbrowser/jobs/${jobid}/tasks/${t.taskId}" class="view_task jt_slide_right">Attempts</a></td>
+					<td><a href="/jobbrowser/jobs/${jobid}/tasks/${t.taskId}" data-row-selector="true">Attempts</a></td>
 				</tr>
 				%endfor
 		</tbody>
@@ -105,6 +105,7 @@
 			    "bFilter": false,
 				"bInfo": false,
 			});
+			$("a[data-row-selector='true']").jHueRowSelector();
 		});
 	</script>
 

+ 3 - 1
apps/jobsub/src/jobsub/templates/list_designs.mako

@@ -72,7 +72,7 @@ ${layout.menubar(section='designs')}
                            data-param-url="${ url('jobsub.views.get_design_params', design_id=design.id) }"
                            data-submit-url="${ url('jobsub.views.submit_design', design_id=design.id) }">Submit</a>
                         <a title="Edit ${design.name}" class="btn small"
-                           href="${ url('jobsub.views.edit_design', design_id=design.id) }">Edit</a>
+                           href="${ url('jobsub.views.edit_design', design_id=design.id) }" data-row-selector="true">Edit</a>
                     %endif%
                     %if currentuser.is_superuser or currentuser.username == design.owner.username:
                         <a title="Delete ${design.name}" class="btn small deleteConfirmation"
@@ -211,6 +211,8 @@ ${layout.menubar(section='designs')}
             $("#installSamples").modal("show");
         });
 
+		$("a[data-row-selector='true']").jHueRowSelector();
+
 
     });
 </script>

+ 3 - 1
apps/useradmin/src/useradmin/templates/list_groups.mako

@@ -57,7 +57,7 @@ ${layout.menubar(section='groups')}
             <td>${', '.join([perm.app + "." + perm.action for perm in group_permissions(group)])}</td>
             %if user.is_superuser == True:
             <td class="right">
-              <a title="Edit ${group.name}" class="btn small editGroupBtn" href="${ url('useradmin.views.edit_group', name=urllib.quote(group.name)) }">Edit</a>
+              <a title="Edit ${group.name}" class="btn small editGroupBtn" href="${ url('useradmin.views.edit_group', name=urllib.quote(group.name)) }" data-row-selector="true">Edit</a>
               <a title="Delete ${group.name}" class="btn small confirmationModal" alt="Are you sure you want to delete ${group.name}?" href="javascript:void(0)" data-confirmation-url="${ url('useradmin.views.delete_group', name=urllib.quote_plus(group.name)) }">Delete</a>
             </td>
             %endif
@@ -126,6 +126,8 @@ ${layout.menubar(section='groups')}
 
             });
 
+			$("a[data-row-selector='true']").jHueRowSelector();
+
         });
     </script>
 

+ 3 - 1
apps/useradmin/src/useradmin/templates/list_permissions.mako

@@ -52,7 +52,7 @@ ${layout.menubar(section='permissions')}
             <td>${', '.join([group.name for group in Group.objects.filter(grouppermission__hue_permission=perm).order_by('name')])}</td>
 			%if user.is_superuser == True:
             <td class="right">
-              <a title="Edit permission" class="btn small editPermissionBtn" data-url="${ url('useradmin.views.edit_permission', app=urllib.quote(perm.app), priv=urllib.quote(perm.action)) }" data-name="${perm.app}">Edit</a>
+              <a title="Edit permission" class="btn small editPermissionBtn" data-url="${ url('useradmin.views.edit_permission', app=urllib.quote(perm.app), priv=urllib.quote(perm.action)) }" data-name="${perm.app}" data-row-selector="true">Edit</a>
             </td>
 			%endif
           </tr>
@@ -114,6 +114,8 @@ ${layout.menubar(section='permissions')}
 				$("#editPermissionFrame").contents().find('form').submit();
 			});
 
+			$("a[data-row-selector='true']").jHueRowSelector();
+
 
 		});
 	</script>

+ 3 - 1
apps/useradmin/src/useradmin/templates/list_users.mako

@@ -62,7 +62,7 @@ ${layout.menubar(section='users')}
                 <td>${date(listed_user.last_login)} ${time(listed_user.last_login).replace("p.m.","PM").replace("a.m.","AM")}</td>
                 <td class="right">
                 %if user.is_superuser == True:
-                    <a title="Edit ${listed_user.username}" class="btn small" href="${ url('useradmin.views.edit_user', username=urllib.quote(listed_user.username)) }">Edit</a>
+                    <a title="Edit ${listed_user.username}" class="btn small" href="${ url('useradmin.views.edit_user', username=urllib.quote(listed_user.username)) }" data-row-selector="true">Edit</a>
                     <a title="Delete ${listed_user.username}" class="btn small confirmationModal" alt="Are you sure you want to delete ${listed_user.username}?" href="javascript:void(0)" data-confirmation-url="${ url('useradmin.views.delete_user', username=urllib.quote_plus(listed_user.username)) }">Delete</a>
                 %else:
                     %if user.username == listed_user.username:
@@ -155,6 +155,8 @@ ${layout.menubar(section='users')}
                 $("#syncLdapFrame").contents().find('form').submit();
             });
 
+			$("a[data-row-selector='true']").jHueRowSelector();
+
         });
     </script>
 

+ 1 - 1
desktop/core/src/desktop/templates/common_header.mako

@@ -44,9 +44,9 @@ from desktop.lib.i18n import smart_unicode
   <script src="/static/ext/js/jquery/jquery-1.7.1.min.js"></script>
   <script src="/static/js/Source/jHue/jquery.showusername.js"></script>
   <script src="/static/js/Source/jHue/jquery.filechooser.js"></script>
-  <script src="/static/js/Source/jHue/jquery.contextmenu.js"></script>
   <script src="/static/js/Source/jHue/jquery.selector.js"></script>
   <script src="/static/js/Source/jHue/jquery.alert.js"></script>
+  <script src="/static/js/Source/jHue/jquery.rowselector.js"></script>
   <script src="/static/ext/js/jquery/plugins/jquery.simpleplaceholder.js"></script>
   <script src="/static/ext/js/jquery/plugins/jquery.dataTables.1.8.2.min.js"></script>
   <script src="/static/ext/js/bootstrap.min.js"></script>

+ 1 - 1
desktop/core/src/desktop/templates/common_header_iframe.html

@@ -37,7 +37,7 @@ limitations under the License.
 	<script src="/static/ext/js/jquery/jquery-1.7.1.min.js"></script>
 	<script src="/static/js/Source/jHue/jquery.showusername.js"></script>
 	<script src="/static/js/Source/jHue/jquery.filechooser.js"></script>
-	<script src="/static/js/Source/jHue/jquery.contextmenu.js"></script>
+	<script src="/static/js/Source/jHue/jquery.rowselector.js"></script>
 	<script src="/static/js/Source/jHue/jquery.selector.js"></script>
 	<script src="/static/js/Source/jHue/jquery.alert.js"></script>
 	<script src="/static/ext/js/jquery/plugins/jquery.simpleplaceholder.js"></script>

+ 0 - 108
desktop/core/static/js/Source/jHue/jquery.contextmenu.js

@@ -1,108 +0,0 @@
-/*
-* jHue contextMenu plugin
-*/
-;(function ($, window, document, undefined) {
-
-	var pluginName = "jHueContextMenu",
-	defaults = {
-		on: "click",
-		items: []
-	};
-
-	function Plugin(element, options) {
-		this.element = element;
-		this.options = $.extend({}, defaults, options) ;
-		this._defaults = defaults;
-		this._name = pluginName;
-		this.init();
-	}
-	
-	Plugin.prototype.setOptions = function(options) {
-		this.options = $.extend({}, defaults, options) ;
-	};
-
-	Plugin.prototype.init = function () {
-		$(".contextMenu").hide();
-		var _this = this;
-		var _ctx;
-		if ($("#jHueContextMenu").length == 0){
-			_ctx = $("<ul>");
-			_ctx.attr("id","jHueContextMenu");
-			_ctx.addClass("dropdown-menu").addClass("contextMenu");
-			_ctx.appendTo("body");
-		}
-		else {
-			_ctx = $("#jHueContextMenu");
-			_ctx.empty();
-		}
-		_ctx.hide();
-		
-		$(this.element).mousedown(function(e){
-			//e.preventDefault();
-			switch (e.which){
-				case 1: 
-					if (_this.options.on == "click"){
-						_ctx.empty();
-						if (_this.options.items.length > 0){
-							$(_this.options.items).each(function(cnt, item){
-								var _item = $("<li>").addClass("contextItem");
-								if (item.divider){
-									_item.addClass("divider");
-								}
-								else {
-									var _link = $("<a>").text(item.text).attr("href","javascript:void(0)");
-									_link.appendTo(_item);
-									if (item.onSelect){
-										_link.click(function(){
-											item.onSelect();
-											_ctx.hide();
-										});
-									}
-								}
-								_item.appendTo(_ctx);
-							});
-						}
-						else {
-							$("#menu"+$(_this.element).attr("data-menuid")).find("li").clone().click(function(){
-								window.setTimeout(function(){
-									_ctx.hide();
-								}, 100);
-							}).appendTo(_ctx);
-						}
-						
-						var _left = (e.pageX+_ctx.width()>$(document).width())?($(document).width()-_ctx.width()-5):e.pageX;
-						
-						_ctx.toggle().css({
-							left: _left, 
-							top: e.pageY
-						});
-						
-					}
-					break;
-				case 3:
-					if (_this.options.on == "rightClick"){
-					}
-					break;
-			}
-		});
-
-		$("body").mousedown(function(e){
-			if (!($(e.target).hasClass("contextEnabler")) && !($(e.target).hasClass("contextItem"))){
-				_ctx.hide();
-			}
-		});
-		
-	};
-
-	$.fn[pluginName] = function (options) {
-		return this.each(function () {
-			if (!$.data(this, 'plugin_' + pluginName)) {
-				$.data(this, 'plugin_' + pluginName, new Plugin( this, options));
-			}
-			else {
-				$.data(this, 'plugin_' + pluginName).setOptions(options);
-			}
-		});
-	}
-
-})(jQuery, window, document );

+ 48 - 0
desktop/core/static/js/Source/jHue/jquery.rowselector.js

@@ -0,0 +1,48 @@
+/*
+* jHue row selector plugin
+* 
+*/
+;(function ($, window, document, undefined) {
+
+	var pluginName = "jHueRowSelector",
+	defaults = {
+	};
+
+	function Plugin(element, options) {
+		this.element = element;
+		this.options = $.extend({}, defaults, options) ;
+		this._defaults = defaults;
+		this._name = pluginName;
+		this.init();
+	}
+	
+	Plugin.prototype.setOptions = function(options) {
+		this.options = $.extend({}, defaults, options) ;
+	};
+
+	Plugin.prototype.init = function () {
+		var _this = this;		
+        $(_this.element).closest("tr").click(function(e){
+            if (!$(e.target).is("a")){
+                if ($.trim($(_this.element).attr("href")) != ""){
+                    location.href = $(_this.element).attr("href");
+                }
+                else {
+                    $(_this.element).click();
+                }
+            }
+        }).css("cursor","pointer");
+	};
+
+	$.fn[pluginName] = function (options) {
+		return this.each(function () {
+			if (!$.data(this, 'plugin_' + pluginName)) {
+				$.data(this, 'plugin_' + pluginName, new Plugin( this, options));
+			}
+			else {
+				$.data(this, 'plugin_' + pluginName).setOptions(options);
+			}
+		});
+	}
+
+})(jQuery, window, document);