Wednesday, July 3, 2013

Spring roo table column title

I wanted to add a tooltip to the columns in my table and I am using table.tagx by Spring Roo.
Because of the limitations in this tag you can't do it without changeing the tag library itself , I was able to do it and below are the steps to do that
  •  In the the table tag file where we are trying to add a new column to this table , under the td tag I defined the parameter title as  title ="${colTxt}".
  • But the colTxt is defined inside the td tag , so in order to allow the above to run we will have to define the colTxt filter before td like below

<c:set var="colTxt">
<spring:eval expression="item[column]" htmlEscape="false" />
</c:set>

Now the table will show tooltip/title for the columns in it.

Just in case if you need the whole tag file below is a copy paste of table.tagx file


 <jsp:root xmlns:c="http://java.sun.com/jsp/jstl/core" xmlns:fn="http://java.sun.com/jsp/jstl/functions" xmlns:util="urn:jsptagdir:/WEB-INF/tags/util" xmlns:spring="http://www.springframework.org/tags" xmlns:form="http://www.springframework.org/tags/form" xmlns:fmt="http://java.sun.com/jsp/jstl/fmt" xmlns:jsp="http://java.sun.com/JSP/Page" version="2.0">
  <jsp:directive.tag import="java.util.ArrayList" />
  <jsp:output omit-xml-declaration="yes" />
  <jsp:directive.attribute name="id" type="java.lang.String" required="true" rtexprvalue="true" description="The identifier for this tag (do not change!)" />
  <jsp:directive.attribute name="data" type="java.util.Collection" required="true" rtexprvalue="true" description="The collection to be displayed in the table" />
  <jsp:directive.attribute name="path" type="java.lang.String" required="true" rtexprvalue="true" description="Specify the URL path" />
  <jsp:directive.attribute name="typeIdFieldName" type="java.lang.String" required="false" rtexprvalue="true" description="The identifier field name for the type (defaults to 'id')" />
  <jsp:directive.attribute name="create" type="java.lang.Boolean" required="false" rtexprvalue="true" description="Include 'create' link into table (default true)" />
  <jsp:directive.attribute name="update" type="java.lang.Boolean" required="false" rtexprvalue="true" description="Include 'update' link into table (default true)" />
  <jsp:directive.attribute name="delete" type="java.lang.Boolean" required="false" rtexprvalue="true" description="Include 'delete' link into table (default true)" />
  <jsp:directive.attribute name="render" type="java.lang.Boolean" required="false" rtexprvalue="true" description="Indicate if the contents of this tag and all enclosed tags should be rendered (default 'true')" />
  <jsp:directive.attribute name="z" type="java.lang.String" required="false" description="Used for checking if element has been modified (to recalculate simply provide empty string value)" />
  <c:if test="${empty render or render}">
    <c:set var="columnProperties" scope="request" />
    <c:set var="columnLabels" scope="request" />
    <c:set var="columnMaxLengths" scope="request" />
    <c:set var="columnTypes" scope="request" />
    <c:set var="columnDatePatterns" scope="request" />
    <jsp:doBody />
    <c:if test="${empty typeIdFieldName}">
      <c:set var="typeIdFieldName" value="id" />
    </c:if>
    <c:if test="${empty update}">
     <c:set var="update" value="true" />
     
    </c:if>
    <c:if test="${empty delete}">
    <!-- Added by Sajjad , if this is an admin user then he should be able to delete a best practice otherwise no      -->
<!--
       <c:choose>
   <c:when test="${user.admin}">
    <c:set var="delete" value="true" />
   </c:when>
   <c:otherwise>
    <c:set var="delete" value="true" />
   </c:otherwise>
    </c:choose>
 -->
        <c:set var="delete" value="true" />
     
<!--         <c:set var="delete" value="true" />  -->
    </c:if>
    <spring:message var="typeName" code="menu_item_${fn:toLowerCase(fn:split(id,'_')[fn:length(fn:split(id,'_')) - 1])}_new_label" htmlEscape="false" />
    <c:set var="lengths" value="${fn:split(columnMaxLengths, '&#9999;')}" scope="request" />
    <c:set var="types" value="${fn:split(columnTypes, '&#9999;')}" scope="request" />
    <c:set var="patterns" value="${fn:split(columnDatePatterns, '&#9999;')}" scope="request" />
    <spring:eval var="colCounter" expression="1" />
    <table>
      <thead>
        <tr>
          <c:forTokens items="${columnLabels}" delims="${'&#9999;'}" var="columnHeading">
            <th>
              <c:out value="${columnHeading}" />
              <spring:eval var="colCounter" expression="colCounter  + 1" />
            </th>
          </c:forTokens>
          <th></th>
          <c:if test="${update}">
            <th></th>
            <spring:eval var="colCounter" expression="colCounter  + 1" />
          </c:if>
          <c:if test="${delete}">
            <th></th>
            <spring:eval var="colCounter" expression="colCounter  + 1" />
          </c:if>
        </tr>
      </thead>
      <c:forEach items="${data}" var="item">
        <tr>
          <c:forTokens items="${columnProperties}" delims="${'&#9999;'}" var="column" varStatus="num">
            <c:set var="columnMaxLength" value="${lengths[num.count-1]}" />
            <c:set var="columnType" value="${types[num.count-1]}" />
            <c:set var="columnDatePattern" value="${patterns[num.count-1]}" />
            <c:set var="colTxt">
              <spring:eval expression="item[column]" htmlEscape="false" />
            </c:set>
          
            <td title="${colTxt}">
              <c:choose>
                <c:when test="${columnType eq 'date'}">
                  <spring:escapeBody>
                    <fmt:formatDate value="${item[column]}" pattern="${fn:escapeXml(columnDatePattern)}" var="colTxt" />
                  </spring:escapeBody>
                </c:when>
                <c:when test="${columnType eq 'calendar'}">
                  <spring:escapeBody>
                    <fmt:formatDate value="${item[column].time}" pattern="${fn:escapeXml(columnDatePattern)}" var="colTxt"/>
                  </spring:escapeBody>
                </c:when>
                <c:otherwise>
<!--                   <c:set var="colTxt">
                     <spring:eval expression="item[column]" htmlEscape="false" />
                   </c:set> -->
                </c:otherwise>
              </c:choose>
              <c:if test="${columnMaxLength ge 0}">
                <c:set value="${fn:substring(colTxt, 0, columnMaxLength)}" var="colTxt" />
              </c:if>
              <c:out value="${colTxt}" />
            </td>
          </c:forTokens>
          <c:set var="itemId"><spring:eval expression="item[typeIdFieldName]"/></c:set>
          <td class="utilbox">
            <spring:url value="${path}/${itemId}" var="show_form_url" />
            <spring:url value="/resources/images/show.png" var="show_image_url" />
            <spring:message arguments="${typeName}" code="entity_show" var="show_label" htmlEscape="false" />
            <a href="${show_form_url}" alt="${fn:escapeXml(show_label)}" title="${fn:escapeXml(show_label)}">
              <img alt="${fn:escapeXml(show_label)}" class="image" src="${show_image_url}" title="${fn:escapeXml(show_label)}" />
            </a>
          </td>
          <c:if test="${update}">
            <td class="utilbox">
            <!-- Added by sajjad if the user is not the creator of this record then don't show update link  -->
             <c:if test="${item.networkId == user.networkId}">
           
               <spring:url value="${path}/${itemId}" var="update_form_url">
                 <spring:param name="form" />
               </spring:url>
               <spring:url value="/resources/images/update.png" var="update_image_url" />
               <spring:message arguments="${typeName}" code="entity_update" var="update_label" htmlEscape="false" />
               <a href="${update_form_url}" alt="${fn:escapeXml(update_label)}" title="${fn:escapeXml(update_label)}">
                 <img alt="${fn:escapeXml(update_label)}" class="image" src="${update_image_url}" title="${fn:escapeXml(update_label)}" />
               </a>
           </c:if>   
            </td>
          </c:if>
          <c:if test="${delete}">
            <td class="utilbox">
              <!-- Added by sajjad if the user is not the creator of this record then don't show delete link  -->
              <c:if test="${item.networkId == user.networkId}">
               <spring:url value="${path}/${itemId}" var="delete_form_url" />
               <spring:url value="/resources/images/delete.png" var="delete_image_url" />
               <form:form action="${delete_form_url}" method="DELETE">
                 <spring:message arguments="${typeName}" code="entity_delete" var="delete_label" htmlEscape="false" />
                 <c:set var="delete_confirm_msg">
                   <spring:escapeBody javaScriptEscape="true">
                     <spring:message code="entity_delete_confirm" />
                   </spring:escapeBody>
                 </c:set>
                 <input alt="${fn:escapeXml(delete_label)}" class="image" src="${delete_image_url}" title="${fn:escapeXml(delete_label)}" type="image" value="${fn:escapeXml(delete_label)}" onclick="return confirm('${delete_confirm_msg}');" />
                 <c:if test="${not empty param.page}">
                   <input name="page" type="hidden" value="1" />
                 </c:if>
                 <c:if test="${not empty param.size}">
                   <input name="size" type="hidden" value="${fn:escapeXml(param.size)}" />
                 </c:if>
               </form:form>
            </c:if>  
            </td>
          </c:if>
        </tr>
      </c:forEach>
      <tr class="footer">
        <td colspan="${colCounter}">
          <c:if test="${empty create or create}">
            <span class="new">
              <spring:url value="${path}" var="create_url">
                <spring:param name="form" />
              </spring:url>
              <a href="${create_url}">
                <spring:url value="/resources/images/add.png" var="create_img_url" />
                <spring:message arguments="${typeName}" code="global_menu_new" var="add_message" htmlEscape="false" />
                <img alt="${fn:escapeXml(add_message)}" src="${create_img_url}" title="${fn:escapeXml(add_message)}" />
              </a>
            </span>
            <c:out value=" " />
          </c:if>
          <c:if test="${not empty maxPages}">
            <util:pagination maxPages="${maxPages}" page="${param.page}" size="${param.size}" />
          </c:if>
        </td>
      </tr>
    </table>
  </c:if>
</jsp:root>