JSP TableView Sorting Problem

I have been trying to get a tableview to be sortable by clicking on the header of columns.  I have been reviewing existing threads on the forum in particular the one below.
https://forums.sdn.sap.com/thread.jspa?threadID=16417
I seem to understand the concept but for some reason my table does not sort, it just does nothing.  Could someone take a look and see if you can find any problems - I can't wait to give points.
Here is all my code.
Here is the Java....
package MSSPackage;
import MSSBeanPackage.PositionOverviewBean;
import MSSPackage.SortTableModel;
import com.sapportals.htmlb.page.DynPage;
import com.sapportals.htmlb.page.PageException;
import com.sapportals.portal.htmlb.page.JSPDynPage;
import com.sapportals.portal.htmlb.page.PageProcessorComponent;
import com.sapportals.portal.prt.component.IPortalComponentContext;
import com.sapportals.portal.prt.component.IPortalComponentProfile;
import com.sapportals.portal.prt.component.IPortalComponentRequest;
import com.sapportals.portal.prt.component.IPortalComponentSession;
import com.sapportals.htmlb.event.*;
import com.sapportals.htmlb.*;
import com.sapportals.htmlb.table.*;
import com.sapportals.htmlb.table.DefaultTableViewModel;
import javax.servlet.http.*;
// SAP RFC Imports
import com.sap.mw.jco.IFunctionTemplate;
import com.sap.mw.jco.JCO;
import com.sapportals.portal.prt.service.jco.IJCOClientPoolEntry;
import com.sapportals.portal.prt.service.jco.IJCOClientService;
import com.sapportals.portal.prt.runtime.PortalRuntime;
import java.util.*;
public class PositionOverview extends PageProcessorComponent {
  public DynPage getPage(){
     return new PositionOverviewDynPage();
  public static class PositionOverviewDynPage extends JSPDynPage{
     JCO.Repository mRepository;
     public JCO.Table tblRelations;
     public JCO.Table tblPositions;     
     public SortTableModel tableModel;
     public int visibleRow = 1;     
     private boolean OrgUnitSelected = false;
     public void doInitialization(){
          IPortalComponentSession oSession = ((IPortalComponentRequest)getRequest()).getComponentSession();
          PositionOverviewBean oBean = new PositionOverviewBean();
          // Table Start row
          oBean.setvisibleRow(new Integer(this.visibleRow).toString());          
          oSession.putValue("myBean", oBean);
          // Define request, context and profile containers         
          IPortalComponentRequest request = (IPortalComponentRequest) this.getRequest();
          IPortalComponentContext myContext = request.getComponentContext();
          IPortalComponentProfile myProfile = myContext.getProfile();
          // Define bean reference to bean
          PositionOverviewBean myBean = new PositionOverviewBean();
          // Table Start row
          myBean.setvisibleRow(new Integer(this.visibleRow).toString());
          // Place bean in user profile.          
          myProfile.putValue("myBean", myBean);
     public void doProcessAfterInput() throws PageException {
     public void doProcessBeforeOutput() throws PageException {
          String NavType = "RCORGUNIT";
          String OType = "O";
          //String OBjid = "10004399";
          String OBjid = "";
          String sapSystem = "SAP_R3_HumanResources";          
          IPortalComponentSession oSession = ((IPortalComponentRequest)getRequest()).getComponentSession();
          PositionOverviewBean myBean = (PositionOverviewBean) oSession.getValue("myBean");
          // Define request, context and profile containers         
          IPortalComponentRequest request = (IPortalComponentRequest) this.getRequest();
/*          IPortalComponentContext myContext = request.getComponentContext();
          IPortalComponentProfile myProfile = myContext.getProfile();
          //HttpSession session = request.getServletRequest().getSession();          //dmm
          //Get Bean from Profile
          PositionOverviewBean myBean = (PositionOverviewBean) myProfile.getValue("myBean");
          //PositionOverviewBean myDataBean = (PositionOverviewBean) session.getValue("POviewBean");               //dmm
          String ddlbSelection = "";
          String ddlbValue = "";
          DropdownListBox ddlbOrgUnits = (DropdownListBox) getComponentByName("ddlbOrgUnits");
          if (ddlbOrgUnits != null)
               ddlbSelection = ddlbOrgUnits.getSelection();
               ddlbValue = ddlbOrgUnits.getValueAsDataType().getValueAsString();
               OBjid = ddlbValue;
               myBean.setObjId(OBjid);
          else
               OBjid = "";
               myBean.setObjId(OBjid);                 
          IJCOClientService clientService;
          IJCOClientPoolEntry poolEntry;          
          JCO.Client client;          
          try
               clientService = (IJCOClientService) PortalRuntime.getRuntimeResources().getService(IJCOClientService.KEY);
               poolEntry = clientService.getJCOClientPoolEntry(sapSystem, request);
               client = poolEntry.getJCOClient();
            // connect to SAP system, logon
               client.connect();
            // Create Jco Repository Object
               mRepository = new JCO.Repository("R3USERMENU", client);
            // Reset function object
               JCO.Function function = null;
            // Run RFC Module on SAP system
               function = this.createFunction("HRWPC_GET_NAV_OBJECTS");
               JCO.ParameterList input = function.getImportParameterList();
               input.setValue("RCORGUNIT", "NAVTYPE");               
               client.execute(function);
               tblRelations = function.getTableParameterList().getTable("RESULT_OBJEC");
               myBean.setRowcnt(tblRelations.getNumRows());
               if (tblRelations.getNumRows() != 0)               
                    myBean.setOrgUnits(tblRelations);
                    if (ddlbOrgUnits == null)
                         // check to see if there is not a position id already assigned
                         tblRelations.setRow(0);
                         OBjid = tblRelations.getString("OBJID");
                         myBean.setObjId(OBjid);
                         //myBean.sTemp = OBjid;                         
               // GET THE POSITION DETAILS
               function = null;
               input = null;
               function = this.createFunction("Z_GET_POSITION_OVERVIEW");
               input = function.getImportParameterList();               
               input.setValue(NavType, "NAVTYPE");               
               input.setValue(OType, "OTYPE");
               input.setValue(OBjid, "OBJID");               
               client.execute(function);
               tblPositions = function.getTableParameterList().getTable("RESULT_OBJEC");
               myBean.setRowcnt(tblPositions.getNumRows());
               tableViewFormat();
               tableModel.setTesting("Startxxxx");
               myBean.settableModel(tableModel);
               //tableModel.setTesting("SSSS");               
               //myDataBean.settableModel(tableModel);                                             //dmm               
               //session.setAttribute("POviewBean", myDataBean);                                //dmm
               oSession.putValue("myBean", myBean);
          //Release pool entry
          poolEntry.release();                           
       catch(Exception ex)
            //name = ex.getMessage();                         
       //String sTest = "this is a test";      
       //request.getComponentSession().putValue("Test", sTest);
       //myProfile.putValue("Testx", sTest);
       this.setJspName("PositionOverviewJSP.jsp");
     public void getPositions()
          String NavType;
          String Root_Ot;
          String Root_ObjId;
     public void tableViewFormat()
          // Define the vectors used to build tableView
          Vector tempRec = new Vector();
          Vector dataRec = new Vector();
          String sDate = "";
          String sPosLink = "";
          String sPosVal = "";
          String sENameLink = "";
          String sENameVal = "";
          String sStatus = "";
          // Loop at company code list and add to vectors
          for (int i = 0; i < tblPositions.getNumRows(); i++)
               tblPositions.setRow(i);
               tempRec = new Vector();
               sStatus = (String) tblPositions.getString("STATUS");
               if (sStatus != null)
                    if (sStatus.equals("0"))                    
                         sDate = tblPositions.getString("ZHR_VACANT_BEGDA");
                         sDate = sDate.substring(5, 7) + "/" + sDate.substring(8, 10) + "/" +  sDate.substring(0, 4);                         
                    else
                         sDate = "";                    
               sPosVal = tblPositions.getString("STEXT");
               sENameVal = tblPositions.getString("ENAME");
               if (sPosVal.equals(""))
                    sPosLink = sPosVal;
               else
                    sPosLink = "<a HREF="myLink" onclick="return EPCM.doNavigate('ROLES://portal_content/com.sap.portal.migrated/ep_5.0/pages/com.sap.pct.hcm.positionprofile?CKey=000000" + tblPositions.getString("OBJID") + "', 1)">" + tblPositions.getString("STEXT") + "</a>";
               if (sENameVal.equals(""))
                    sENameLink = sENameVal;
               else
                    sENameLink = "<a HREF="myLink" onclick="return EPCM.doNavigate('ROLES://portal_content/com.phi/com.phi.mgt/com.phi.mss/com.phi.hr/com.phi.pages/com.phi.mgt.mss.hr.pages.positionholder?CKey=000000" + tblPositions.getString("OBJID") + "', 1)">" + tblPositions.getString("ENAME") + "</a>";
               tempRec.addElement(sStatus);
               tempRec.addElement(tblPositions.getString("OBJID"));
               tempRec.addElement(sPosLink);
               tempRec.addElement(sENameLink);
               tempRec.addElement(sDate);               
               dataRec.addElement(tempRec);
          // Then define the technical column names
          Vector colNames = new Vector();
          colNames.addElement("STATUS");
          colNames.addElement("OBJID");
          colNames.addElement("STEXT");     
          colNames.addElement("ENAME");
          colNames.addElement("ZHR_VACANT_BEGDA");
          // Now we build the actual tableView
          //tableModel = new DefaultTableViewModel(dataRec, colNames);
          tableModel = new SortTableModel(dataRec, colNames, 5);     
          // Define tableView parameters
          tableModel.setKeyColumn(2);
          TableColumn column = tableModel.getColumn("STATUS");
          column.setEncode(false);
          column.setType(com.sapportals.htmlb.enum.TableColumnType.USER);
          column.setTitle("Vacant");
          column = tableModel.getColumn("OBJID");
          column.setTitle("Position Number");
          column = tableModel.getColumn("STEXT");
          column.setTitle("Position");
          column = tableModel.getColumn("ENAME");
          column.setTitle("Holder of Position");          
          column = tableModel.getColumn("ZHR_VACANT_BEGDA");
          column.setTitle("Vacant as of");
     //     * Navigation Button Clicked
     public void myOnNavigate(Event event)
          TableNavigationEvent tne = (TableNavigationEvent) event;
          visibleRow = tne.getFirstVisibleRowAfter();
          // Define request, context and profile containers         
          IPortalComponentRequest request = (IPortalComponentRequest) this.getRequest();
          IPortalComponentContext myContext = request.getComponentContext();
          IPortalComponentProfile myProfile = myContext.getProfile();
          // Get Bean from profile
          PositionOverviewBean myBean = (PositionOverviewBean) myProfile.getValue("myBean");
          // Table Start row
          myBean.setvisibleRow(new Integer(this.visibleRow).toString());
     public void onHeaderClick(Event event)
          IPortalComponentSession oSession = ((IPortalComponentRequest)getRequest()).getComponentSession();
          PositionOverviewBean myBean = (PositionOverviewBean) oSession.getValue("myBean");
          TableHeaderClickEvent tne = (TableHeaderClickEvent) event; // get the event
          SortTableModel tblModel = myBean.gettableModel();
          //tblModel.sort();
          int col = 3;
          tblModel.sortByColumn(col);
          myBean.settableModel(tblModel);
          oSession.putValue("myBean", myBean);
     // Create Function object for RFC Calls
     public JCO.Function createFunction(String name) throws Exception
          try
               IFunctionTemplate ft = mRepository.getFunctionTemplate(name.toUpperCase());
               if (ft == null)
                    return null;
               return ft.getFunction();
          catch (Exception ex)
               ex.printStackTrace();
               throw new Exception("Problem retrieving JCO.Function object");
     public void onSelectddlbOrgUnits(Event event) throws PageException
          OrgUnitSelected = true;          
Here is the JSP
<%@ page import="com.sap.mw.jco.*" %>
<%@ page import="com.sapportals.htmlb.enum.*" %>
<%@ page import="MSSPackage.TableViewCellRenderer" %>
<%@ page import="com.sapportals.portal.prt.component.IPortalComponentRequest" %>
<%@ page import="javax.servlet.http.*" %>
<%@ page import="com.sapportals.portal.prt.component.IPortalComponentContext" %>
<%@ taglib uri="tagLib" prefix="hbj" %>
<hbj:content id="myContext" >
     <hbj:page title="PageTitle">
          <hbj:form id="myFormId" >  
          <jsp:useBean id="myBean" scope="session" class="MSSBeanPackage.PositionOverviewBean" />     
               <hbj:gridLayout rowSize="1" columnSize="1" cellSpacing="1">
                    <hbj:gridLayoutCell columnIndex="1" rowIndex="1">
                         <hbj:textView id="ddlbLable" text="Select organizational unit to display positions" design="STANDARD" />
                    </hbj:gridLayoutCell>                         
                    <hbj:gridLayoutCell columnIndex="1" rowIndex="2">
                         <hbj:dropdownListBox id="ddlbOrgUnits" onSelect="onSelectddlbOrgUnits" selection="<%=myBean.getObjId()%>">                                                       
                              <%                         
                                   JCO.Table org_units = null;                                                       
                                   org_units = myBean.getOrgUnits();
                                   for (int i = 0; i < org_units.getNumRows(); i++)
                                        org_units.setRow(i);
                                        String sUnit = org_units.getString("STEXT");
                                        String Unit_Id = org_units.getString("OBJID");
                              %>
                              <hbj:listBoxItem key="<%=Unit_Id%>" value="<%=sUnit%>" />
                              <%
                              %>
                         </hbj:dropdownListBox>                                                                                                   
                    </hbj:gridLayoutCell>
                    <hbj:gridLayoutCell columnIndex="1" rowIndex="3">
                         <hbj:textView id="listLable" text="To designate a vacant position, click the icon in the 'Create Form' column" design="STANDARD" />                    
                    </hbj:gridLayoutCell>                    
                    <hbj:gridLayoutCell columnIndex="1" rowIndex="4">     
                         <hbj:tableView
                              id="myTableView"
                              headerVisible="true"
                              footerVisible="true"
                              fillUpEmptyRows="true"
                              selectionMode="NONE"                              
                              navigationMode="BYPAGE"
                              onNavigate="myOnNavigate"                                        
                              visibleFirstRow="<%= myBean.getvisibleRow() %>"                                                  
                              visibleRowCount="5" >                                                            
                              <%
                              myTableView.setOnHeaderClick("onHeaderClick");
                              myTableView.setUserTypeCellRenderer(new TableViewCellRenderer());                                                             
                              myTableView.setModel(myBean.gettableModel());
                              myTableView.setColumnType(TableColumnType.LINK, 3);
                              myTableView.setColumnType(TableColumnType.LINK, 4);                              
                              %>
                         </hbj:tableView>
                    </hbj:gridLayoutCell>                                        
               </hbj:gridLayout>   
          </hbj:form>
     </hbj:page>
</hbj:content>
Here is the BEAN
package MSSBeanPackage;
//import com.sapportals.htmlb.enum.TableColumnType;
import MSSPackage.SortTableModel;
import com.sapportals.htmlb.table.DefaultTableViewModel;
//import com.sapportals.htmlb.table.TableColumn;
//import com.sapportals.htmlb.table.TableView;
//import com.sapportals.htmlb.table.TableViewModel;
import com.sap.mw.jco.JCO;
import com.sap.mw.jco.JCO.Table;
public class PositionOverviewBean {
//     public DefaultTableViewModel tableModel;
     public SortTableModel tableModel;
     public JCO.Table OrgUnits;
     public String ObjId;
     public String visibleRow;
     public int rowcnt;
     public String sTemp;
     // Get and Set methods for table model
//     public DefaultTableViewModel gettableModel() { return tableModel; }
//     public void settableModel(DefaultTableViewModel tableModel)     { this.tableModel = tableModel;     }
     public SortTableModel gettableModel() { return tableModel; }
     public void settableModel(SortTableModel IntableModel)     { this.tableModel = IntableModel;     }     
     public JCO.Table getOrgUnits()     { return OrgUnits; }
     public void setOrgUnits(JCO.Table value) { this.OrgUnits = value; }
     // Get and Set methods for visiblerow
     public String getvisibleRow() {     return visibleRow; }
     public void setvisibleRow(String visibleRow) { this.visibleRow = visibleRow; }     
     public int getRowcnt() { return this.rowcnt; }
     public void setRowcnt(int rowcnt) { this.rowcnt = rowcnt; }
     public String getObjId() { return this.ObjId; }
     public void setObjId(String value) { this.ObjId = value; }     
Here is the sorting class
package MSSPackage;
import java.util.Collections;
import java.util.Comparator;
import java.util.Vector;
import com.sapportals.htmlb.table.DefaultTableViewModel;
public class SortTableModel extends DefaultTableViewModel implements Comparator {
     //protected int currCol;
     public int currCol;
     protected Vector ascendCol; // this vector stores the state (ascending or descending) of each column
     protected Integer one = new Integer(1);
     protected Integer minusOne = new Integer(-1);
     public String testing;
     public SortTableModel()
          super();
          ascendCol = new Vector();
     public SortTableModel(Vector vec)
          super(vec);
          ascendCol = new Vector();
     public SortTableModel(Vector vec, Vector vec2, int numberOfColumns)
          super(vec, vec2);
          ascendCol = new Vector();
          setSortOrder(numberOfColumns);
     public int compare (Object v1, Object v2)
          // the comparison is between 2 vectors, each representing a row
          // the comparison is done between 2 objects from the different rows that are in the column that is being sorted
          int ascending = ((Integer)ascendCol.get(currCol)).intValue();
          if (v1 == null && v2 == null)
               return 0;
          else if (v2 == null)
          { // Define null less than everything.
               return 1 * ascending;
          else if (v1 == null)
               return -1 * ascending;
          Object o1 = ((Vector)v1).get(currCol);
          Object o2 = ((Vector)v2).get(currCol);
          // If both values are null, return 0.
          if (o1 == null && o2 == null)
               return 0;
          else if (o2 == null)
          { // Define null less than everything.
               return 1 * ascending;
          else if (o1 == null)
               return -1 * ascending;
          if (o1 instanceof Number && o2 instanceof Number)
               Number n1 = (Number)o1;
               double d1 = n1.doubleValue();
               Number n2 = (Number)o2;
               double d2 = n2.doubleValue();
               if (d1 == d2)
                    return 0;
               else if (d1 > d2)
                    return 1 * ascending;
               else {
                    return -1 * ascending;
          else if (o1 instanceof Boolean && o2 instanceof Boolean)
               Boolean bool1 = (Boolean)o1;
               boolean b1 = bool1.booleanValue();
               Boolean bool2 = (Boolean)o2;
               boolean b2 = bool2.booleanValue();
               if (b1 == b2)
                    return 0;
               else if (b1)
                    return 1 * ascending;
               else
                    return -1 * ascending;
          else
               // default case
               if (o1 instanceof Comparable && o2 instanceof Comparable)
                    Comparable c1 = (Comparable)o1;
                    Comparable c2 = (Comparable)o2; // superflous cast, no need for it!
                    try
                         return c1.compareTo(c2) * ascending;
                    catch (ClassCastException cce)
                    // forget it... we'll deal with them like 2 normal objects below.
               String s1 = o1.toString();
               String s2 = o2.toString();
               return s1.compareTo(s2) * ascending;
     * This method sorts the rows using Java's Collections class.
     * After sorting, it changes the state of the column -
     * if the column was ascending, its new state is descending, and vice versa.
     public void sort()
          Collections.sort(dataVector, this);          
          //Collections.sort(dataVector);
          Integer val = (Integer)ascendCol.get(currCol);
          ascendCol.remove(currCol);
          if (val.equals(one)) // change the state of the column
               ascendCol.add(currCol, minusOne);
          else
               ascendCol.add(currCol, one);
     public void sortByColumn(int column)
          this.currCol = column;
          sort();
     public void setSortOrder(int numberOfColumns)
          for (int i = 0; i < numberOfColumns; i++)
               ascendCol.add(one);
     public void setTesting(String inStr)
          testing = inStr;
Any help would be greatly apprciated and rewarded...

Hi Don,
be aware that after the method onHeaderClick(Event event) is executed the method doProcessBeforeOutput() is executed as well.
I look over your code and found the following:
1) In method onHeaderClick you sort the table model and store the table model in the bean
2) In method doProcessBeforeOutput() you create a new table model from scratch (in helper method tableViewFormat())and store it in the bean. Thus you overwrite the sorted model.
I suggest that you move the initial creation of the table model in method doInitialization(). Do not forget to store the created table in the bean. In method doProcessBeforeOutput() you retrieve the table model from the bean instead of creating a new one for every request.
Best regards,
Martin

Similar Messages

  • Jsp paging & sorting problem

    hi all,
    i am facing a problem while displaiyng my pages. i hav a list of records of which i have to display a predefined no of records at a time,say 6. i am getting the list from database and then putting it in session. on my page i would give links to page numbers to view next set of records, much like what google does.
    now this is working fine. i have an option on my page to sort the set of records, the sorting being done by my query. problem arises when i use this sorting functionality, the sorting is performed on the entire list, not on those which are displayed... the example might make things clearer.
    if i have a 6 records and i display 4 records at a time, so on my page 1 i will be able to view record no. 1, 2, 3, 4. now when i sort them i see record no. 6, 5, 4, 3. ideally i would like to see the records 4, ,3, 2, 1.
    i hope things are clear....what can be done to tackle this...
    thanks in advance...

    Abhi,
    I was wondering if you could explain this to me:
    <% request.setAttribute( "test", new TestList(10, false) ); %>
    on my application, I use database query to get all the data. the method returns vector of objects (query results). Can I use vector instead of List?

  • TableView : sort = "SERVER" ...does not work for "TIME"

    Hi,
    TableView sort = "Server" works automatically for "Date" Fields and "Text" Fields.
    But it does not work for "Time" field with data element "CDUZEIT". It shows the below error message:
    Note
    The following error text was processed in the system IFD : Invalid sort field type in "SORT ... AS TEXT".
    The error occurred on the application server ifdmain_IFD_01 and in the work process 0 .
    The termination type was: RABAX_STATE
    The ABAP call stack was:
    Form: IF_HTMLB_ELEMENT_DELEGATED~DO_AT_END of program CL_HTMLB_TABLEVIEW============CP
    Form: DELEGATED_END of program CL_HTMLB_ELEMENT==============CP
    Form: IF_BSP_ELEMENT~DO_AT_END of program CL_HTMLB_TABLEVIEW============CP
    Form: ONLAYOUT of program CLO27OLHO7EA9KVWPONPDC2NLTDFHCP
    Form: %_ONLAYOUT of program CL_O27OLHO7EA9KVWPONPDC2NLTDFHCP
    Form: DO_REQUEST of program CL_BSP_PAGE===================CP
    Form: CALL_VIEW of program CL_BSP_PAGE_BASE==============CP
    Form: CALL_VIEW of program CL_BSP_CONTROLLER=============CP
    Form: DO_REQUEST of program ZCL_ZPR_C_ACTION_LOG==========CP
    Form: DO_REQUEST of program CL_BSP_CTRL_ADAPTER===========CP
    Thanks and Regards,
    Bindiya

    Welcome to SDN.
    This problem and solution to it is exaplined in the following oss note number.
    <a href="https://service.sap.com/~form/handler?_APP=01100107900000000342&_EVENT=REDIR&_NNUM=893210&_NLANG=E">893210</a>
    Regards
    Raja

  • Sorting Problem in FND_MENU_ENTRIES_TL Table

    Hi,
    FND_MENU_ENTRIES_TL Table storing the record FND_MENU_ENTRIES_TL_N1(MENU_ID,PROMPT,LANGUAGE) wise in R12. But whereas in 11i, records stored FND_MENU_ENTRIES_TL_U1(MENU_ID,ENTRY_SEQUENCE,LANGUAGE).
    I am confused, whether i need to recreate the index in R12, so the records will get store MENU_ID,ENTRY_SEQUENCE,LANGUAGE wise.
    Could any one please suggest me how to resolve this problem.
    Thanks,
    Praba T

    815667 wrote:
    Hi,
    FND_MENU_ENTRIES_TL Table storing the record FND_MENU_ENTRIES_TL_N1(MENU_ID,PROMPT,LANGUAGE) wise in R12. But whereas in 11i, records stored FND_MENU_ENTRIES_TL_U1(MENU_ID,ENTRY_SEQUENCE,LANGUAGE).
    I am confused, whether i need to recreate the index in R12, so the records will get store MENU_ID,ENTRY_SEQUENCE,LANGUAGE wise.
    Could any one please suggest me how to resolve this problem.
    Thanks,
    Praba TPl do not abuse the forums by cross-posting in multiple forums
    Sorting Problem in FND_MENU_ENTRIES_TL Table
    Sorting Problem in FND_MENU_ENTRIES_TL Table
    Your issue is related to EBS, not to database upgrades (which is the topic of this forum)
    Srini

  • Sorting problems in Grid View

    Hi, I'm having a bit of a sorting problem when it comes to an artist with name variations. The example I'm going to use is DJ Tiesto.
    There are album I have where he is credited as DJ Tiesto, and others where he is simply Tiesto.
    In the end, I'd like these albums sorted chronologically under one name (say DJ Tiesto), while still preserving and showing the proper artist name for each album. I have it set to sort by "Album by Year", which is working fine.
    The major problem I am having is that I can't get it to display properly across all iTunes viewing methods: List mode, Grid mode, and Coverflow.
    I've tried leaving the Artist field alone, and changing the Sort Artist field to "DJ Tiesto" for all songs, and that almost works:
    -List mode groups them all under "DJ Tiesto", while showing each albums Artist as the correct artist name.
    -Grid mode sorted by Album groups them all under "DJ Tiesto", while showing each albums Artist as the correct artist name.
    -Coverflow sorts them all in chronological order, while showing each albums Artist as the correct artist name.
    Problem is, Grid mode sorted by ARTIST creates two separate artists! Some for DJ Tiesto and some for Tiesto!
    To correct this I tried changing the Album Artist field for all songs to "DJ Tiesto", which solved that problem but created a bunch of new ones:
    -List mode is still correctly grouping them under "DJ Tiesto", while showing each albums Artist as the correct artist name.
    -Grid mode sorted by Album is still correctly grouping them under "DJ Tiesto", *however now it is not displaying the correct Artist name for each album!*
    -Grid mode sorted by Artist is now grouping them all under "DJ Tiesto", *however it is not displaying the correct Artist name for each album!*
    -Coverflow is sorting them in correct chronological order, *however it as well is not displaying the correct Artist name for each album!*
    Using the Album Artist tag has created more problems that it has solved! Is there anyone who knows a way to achieve what I am trying to do? I have tried seemingly every option I can and have still not found a way to do this!!
    Thanks!

    My own method of working involves renaming the files upon import to:
    i "shotdate_sequencenumber"
    Files are therefore typically named
    b 2007-11-25_001
    etc.
    This way, sorting by Filename automatically sorts by Date by default. And it wouldn't even matter if you added a descriptive text in between the date and number (
    b 2007-11-25_Scotland_001

  • Sorting problem in standard vendor search help

    Hi all,
    I'm enhancing the vendor search help.
    I found that there is a sorting problem in the original standard search help.
    The 1st time to search vendor in the search help returns a correct list, then I just sort the vendor in ascending order. This time the column name of the hit list changes and mismatch the actual values.
    Any one faced this problem before?
    What's wrong are there ?
    Thanks.

    Thanks Peluka.
    But even I don't enhance the vendor search help, I still found that the original standard version has this problem after sorting.
    Is that the program bug?
    Have anyone encountered this problem before?

  • Jsp and JPanel problem

    Hello. I've been to this forum many times, but have always been a bit gunshy about posting anything of my own. Now I have a problem I haven't seen before, so here goes. I have a JPanel in a java program that has all sorts of other componants added to it. I am trying to display the whole thing in a jsp page. This is what I am doing in the java file to return the image ("display" is the JPanel):
    public byte[] getImage(){
        int w = display.getWidth();
        int h = display.getHeight();
        BufferedImage img = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB);
        display.paint(img.createGraphics());
        ByteArrayOutputStream os = new ByteArrayOutputStream();
        ImageIO.write(img, "jpeg", os);
        return os.toByteArray();
    }and then in the jsp page I say:
    <%@ page contentType="image/jpeg" %>
    <%@ page import="myPackage.MyClass" %>
    <%
         MyClass picture = new MyClass();
         byte[] b = picture.getImage();
         OutputStream os;
         os = response.getOutputStream();
         os.write(b);
         os.flush();
    %>And the problem is that the page is displaying a blank JPanel and none of the componants that were added to it. If I save the the JPanel as a jpeg in the java program, though, it does contain all the componants, so I am not sure what I am doing wrong here. If there is some way to get the all the JPanel componants returned, that would be great to know. Thanks for any help.

    nope, that didn't work.
    Maybe I am going about solving the problem all wrong. The JPanel and its componants are kind of like a template. When a user of the system submits their information it automatically puts the data into the template and displays it on screen as a jpg. It works when I save the jpg as a file from the java program but not when i send the byte array to the jsp server. It just shows the blank panel....
    Is there a better way to go about doing this?

  • RequestDispatcher and .jsp "first run" problem

    Hello all,
    I'm testing our app on a development server (rh 8.0, tomcat 4.1.18-LE-jdk14, apache 2.0.44, mod_jk-2.0.43 ). Everything seems to work fine except...
    I have several instances of servlets that call a .jsp, which calls a servlet, which calls another .jsp, etc. My problem is that the servlets have a problem referencing the .jsps the first time each one is called after a tomcat/apache restart. BTW, jsp to jsp calls work perfectly.
    For example, the log-in page calls a servlet which retrieves session and user info from a db and forwards the user to their "home page" that is built in .jsp. The first time I try to log in, I get the following error:
    HTTP Status 500 -
    type Exception report
    message
    description The server encountered an internal error () that prevented it from fulfilling this request.
    exception
    java.lang.NullPointerException
         at com.act.cit.ui.CitGeneralServlet.gotoJSPErrorPage(CitGeneralServlet.java:119)
         at com.act.cit.ui.CitGeneralServlet.cleanUpForException(CitGeneralServlet.java:136)
         at com.act.cit.ui.CitLoginServlet.doPost(CitLoginServlet.java:201)
         at javax.servlet.http.HttpServlet.service(HttpServlet.java:760)
         at javax.servlet.http.HttpServlet.service(HttpServlet.java:853)
         at org.apache.catalina.servlets.InvokerServlet.serveRequest
    So not only am I not accessing the .jsp, but I'm not finding my desginated error .jsp either...looks like the 'null' that is being referenced is the .jsp I'm trying to hit. I've confirmed that the database is being accessed correctly (non-null results) and that I'm getting to the point in my servlet that forwards me to my .jsp:
    req.getRequestDispatcher("../jsp/citMain.jsp").forward(req, res);
    I've also tried:
    getServletContext().getRequestDispatcher("../jsp/citMain.jsp").forward(req, res);
    "req" and "res" both have non-null addresses. The next time I try to log in, everything works perfectly, just as it does on our old production server.
    All I can think of is that there's some sort of problem in the apache/tomcat config, but why would the server be able to process the .jsp successfully on subsequent tries?
    Thanks a lot! This one's really been eating at me!

    What version of tomcat and jdk are you using?rh 8.0, tomcat 4.1.18-LE-jdk14, apache 2.0.44, mod_jk-2.0.43
    I left my first getRequestDispatcher attempt as relative addressing and changed to absolute address on the second just to test:
    rd = req.getRequestDispatcher("../jsp/citMain.jsp");
    if (rd==null){  
         LogFileWriter.logThis(this, "rd was null");  //this is just a static logger I wrote  
         rd = req.getRequestDispatcher("/jsp/citMain.jsp");  
         if (rd==null)     
              LogFileWriter.logThis(this, "rd is still null");  
         else     
              LogFileWriter.logThis(this, "now rd is okay");
    else{  
         LogFileWriter.logThis(this, "rd was okay");
    } Here's my new logfile output after two login attempts:
    CitGeneralServlet--
    rd was null
    CitGeneralServlet--
    now rd is okay
    end of the first attempt, now here's the results of the 2nd attempt:
    CitGeneralServlet--
    rd was okay
    I still think it's odd that I can use relative addresses after the first execution, but I'm sure it's something to do with when the .jsp is compiled. Anyway, I don't have time to dig for the root cause right now. Absolute address seems to fix the problem, I'll stick with that. Thanks for all the suggestions. Hopefully this thread will help someone else who comes across the same problem.

  • Htmlb:TableView title problem

    Hello,
    recently we installed some support packages (now at SP59). After the installation my TableView titles are not shown correctly. Before the installation the titles were displayed completely, now after the installation the width of the column is only determined by the shown values in the columns.
    The problem I have now is that vor a column which only contains the values A or B, the title "Status" is not shown. Any suggestions?
    ALEX

    If you are using an iterator,
    use the method IF_HTMLB_TABLEVIEW_ITERATOR~GET_COLUMN_DEFINITIONS
    there you can edit the width of your columns:
    APPEND INITIAL LINE TO p_column_definitions ASSIGNING <tv_column>.
      <tv_column>-columnname               = c_type.
      <tv_column>-sort                     = c_x.
      <tv_column>-title                    = c_energy_type.
      <tv_column>-disable_filter           = c_x.
      <tv_column>-edit                     = '1'.
      <tv_column>-width                    = 15.
    grtz
    Koen
    Message was edited by: Koen Labie

  • TableView Sort

    Hello,
    I've the below code in my RENDER_CELL_START method and I do see the radio buttons properly on my tableview. The problem is that when I sort the tableview the radio selection is messed up totally. Sometimes more than 1 selection is changed and sometime it changes the selection by itself. I am doinf sort="server" and my tableview is binded to my model class (MVC).
    Any help would be appreciated.
    Thanks.
          WHEN 'DEFSEVERITY'.
            create object rad_gp.
            rbg = cl_htmlb_radiobuttongroup=>factory( id = p_cell_id columncount = '4' ).
            rad_gp->add( element = rbg level = 1 ).
            if c_item_row_ref2->defseverity = 'A'.
               rb ?= cl_htmlb_radiobutton=>factory( id = p_cell_id id_postfix = '1' key = 'A' text = 'A' checked = 'X' ).
            else.
               rb ?= cl_htmlb_radiobutton=>factory( id = p_cell_id id_postfix = '1' key = 'A' text = 'A' ).
            endif.
            rad_gp->add( element = rb level = 2 ).
            if c_item_row_ref2->defseverity = 'B'.
               rb ?= cl_htmlb_radiobutton=>factory( id = p_cell_id id_postfix = '2' key = 'B' text = 'B' checked = 'X' ).
            else.
               rb ?= cl_htmlb_radiobutton=>factory( id = p_cell_id id_postfix = '2' key = 'B' text = 'B' ).
            endif.
            rad_gp->add( element = rb level = 2 ).
            if c_item_row_ref2->defseverity = 'C'.
               rb ?= cl_htmlb_radiobutton=>factory( id = p_cell_id id_postfix = '3' key = 'C' text = 'C' checked = 'X' ).
            else.
               rb ?= cl_htmlb_radiobutton=>factory( id = p_cell_id id_postfix = '3' key = 'C' text = 'C' ).
            endif.
            rad_gp->add( element = rb level = 2 ).
            if c_item_row_ref2->defseverity = 'N'.
               rb ?= cl_htmlb_radiobutton=>factory( id = p_cell_id id_postfix = '4' key = 'N' text = 'None' checked = 'X' ).
            else.
               rb ?= cl_htmlb_radiobutton=>factory( id = p_cell_id id_postfix = '4' key = 'N' text = 'None' ).
            endif.
            rad_gp->add( element = rb level = 2 ).
            p_replacement_bee ?= rad_gp.
          ENDCASE.

    Thanks Ravi,
    I've seen the thread posted by Raja before. Since my tableview is binded (MVC) it is sorting correctly. Only problem is, after sort, the radio button selections are not showing up properly. For example, more than one button is checked in a group. It appears that the radiobutton group information is getting lost somewhere.
    One question - Since render_cell_start fires at every server event - it should mark the selections properly after sorting, correct?
    If I remove my radio button and display the data itself in the column (like A, B, C) it shows up fine and then there is no problem in sorting as well.
    Do I need to create an OSS note for this one?
    I really need this feature implemented.
    Thanks,
    Partho

  • Sort problem in a report

    Hi,
    I'm using the sort on a report with 7 columns. For each column I've specified
    the sort sequence from 1 to 7. The last sort is a date field. If i sort now the
    last column and i change to next report side the sort change jump to the first column.
    Is there somebody who had also a problem like this?
    Greets,
    Tom

    You can check boxes to determine which columns can be sorted; if you check one or more boxes, you also need to set the "Sort Sequence" attribute under the "Report Attributes" tab of your SQL query region. So to use sorting you must.
    1. ensure you don't have an order by in your SQL statement
    2. check one or more "sort" boxes
    3. set the default order in one or more column in the "sort sequence" column
    Hope this helps,
    Mike

  • Sorting Problem in XML Publisher Report

    Dear Members,
    I am facing problems with sorting data in my XML Publisher Report.
    We are using Oracle E-Business Suite 12.1 Version and i developed a rtf Template and executable is an RDF which generates XML Data.
    I want the whole report to group by element ITEM_NAME which is a character in the ascending order. I tried several ways but it is not working properly.
    I don't know how to upload the RTF template in this forum. I tried to post the XML Code and since its excceds 30000 characters i cant post it in the forum.
    Any help is greatly appreciated.
    Thanks
    Sandeep

    You can't upload the template here; you can post a part of the relevant XML code and template code here.
    or send me a sample XML and RTF template to [email protected] and I will take a look.

  • Mail sorting problem after upgrading to Mountain Lion?

    I have a strange problem with Mail after upgrading to Mountain Lion.
    Before upgrading, when I tried to search my Mail Inbox for e-mails from a specific sender, the esearch results would be indexed by the name of the sender. For example: when I entered 'John Smith' in the search box in Mail, it would display a list of email from 'John Smith'
    Now after upgrading, the same query indexes the search results by the 'To' address i.e. my email address.For example: if my name is 'Steve Johnson', a search for 'John Smith' in the search box in Mail displays a list of email to 'Steve Johnson' and not from 'John Smith' which is how it used to display before.
    My emails are sorted by Date always, and I am using the default Mail view [not classic view]
    Can someone please help with a fix for this to help me get back to the original display I had while searching? Thanks in advance.

    I'm having the same problem.  It's incredibly annoying!!!  Did you find an answer?

  • Help with Artist Sort Problem Needed...

    This is a bit long, so I'll start with the three main questions and below them is the backstory and detail of the problem (I did do a search but nothing turned up):
    1) Does anyone know how to fix artist sorting issues where the artists are properly sorted (alphabetically by last name and band name) but there are constant grey-bar letter headings for the first name (sorry...I don't know how to explain better than I do below in detail)
    2) Will re-setting the Touch require I have to...
    a) re-add all the songs I've manually selected again
    b) re-input any data saved to apps (such as CarCare and
    Pocketpedia) and if so, can I backup that data first?
    3) If all the re-doing in 2 above is necessary if I were to re-set the iPod, can anyone think of an alternative fix that would avoid a reset?
    I might be able to get to an Apple store this weekend to ask a "genius" but I'm not that confident in them since I was given some incorrect information on how the Touch handles playlists at the time of original purchase.
    Okay... now, what happened:
    I'm not sure what to make of this, fortunately playback and all main functions are unaffected. I have my iPod Touch 2g set for manual sync. Today, while I was charging it at work, my PC (WinXP) froze. I gave it plenty of time to unfreeze, but eventually had no choice but to do a hard reboot while the iPod said "syncing." I slid the slider to cancel the sync, but the iPod didn't respond. I unhooked it from the PC and it unfroze. I shut it down and re-started.
    Everything seemed fine after the iPod reboot except that now, while the artists are still sorted alphabetically (I've manually set artists to sort by last name), there are headers using the first letter of the first name between each artist. So, for instance, this is how the top of my artist list looks now (lines below with just a letter are the grey divider bar with the alphabetical header):
    R
    Ryan Adams
    D
    Dave Alvin
    T
    Tori Amos
    E
    Eric Andersen
    A
    Apples in Stereo
    Arcade Fire
    L
    Louis Armstrong
    A
    Ataris
    ...etc.
    This problem has not extended to album or song title fields, but for some reason, when scrolling through the album view using the index on the right, it moves fine until "O" -- then it sits still as I scroll down until it gets to "#", at which point it's resposnive again.
    I've checked the music library on the iPod via iTunes and the artist sort fields are still correct.
    Suggestions? I'm new to the Touch and am leery of doing a reset yet since it's taken time to figure out which songs from my 100+gb library to manually put on this. Also, I have no idea how it will affect the apps I've downloaded. There are some where I've saved data (such as CarCare and Pocketpedia) and I REALLY don't want to risk having to re-input all that data.
    To anyone with any words of advice, thanks in advance.
    Message was edited by: IronWaffle
    Message was edited by: IronWaffle

    This is an answer to only qestion 2. Yes restoring your ipod will delete all songs, apps, videos, etc., but you can back up settings like a passcode lock or screen brightness. But it will ask if you want to back up settings. If your'e on windows, in itunes go to file and down almost all the way you will see a "Tranfer purchases from (ex.) steves ipod" and that will make sure you have all your apps and music and other stuff.

  • JTable sorting - problem when adding elements (complete code inside)

    I�m writing this email with reference to a recent posting here but this time with the code example. (I apologize for the duplicated posting � this time it will be with the code)
    Problem: when adding more elements to the JTable (sorted) the exception: ArrayIndexOutOfBoundsException is thrown.
    Example: If the elements in the table are 10 and then the user requests for 8 � the table will produce the correct result. However, if the user will ask for 11 items (>10) the exception will be thrown.
    The program: The program below (compiles and running). A JTable is constructed with 3 items, when you click the button - the return result should be 4 items - this will generate the error, WHY?
    I would highly appreciate your thoughts why this is happening and most importantly � how to fix it.
    Thanks a lot
    3 files:
    (1) TableSorterDemo
    (2) Traveler
    (3)TableSorter
    //TableSorterDemo:
    package sorter;
    import javax.swing.DefaultListModel;
    import javax.swing.JButton;
    import javax.swing.JFrame;
    import javax.swing.JPanel;
    import javax.swing.JScrollPane;
    import javax.swing.JTable;
    import javax.swing.table.AbstractTableModel;
    import java.awt.BorderLayout;
    import java.awt.Dimension;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    * TableSorterDemo is like TableDemo, except that it
    * inserts a custom model -- a sorter -- between the table
    * and its data model.  It also has column tool tips.
    public class TableSorterDemo implements ActionListener
         private JPanel superPanel;
         private JButton clickMe = new JButton("click me to get diff data");
         private boolean DEBUG = false;
         private DefaultListModel defaultListModel;
         private JTable table;
        public TableSorterDemo()
             superPanel = new JPanel(new BorderLayout());
             defaultListModel = new DefaultListModel();
             init1();
            TableSorter sorter = new TableSorter(new MyTableModel(defaultListModel)); //ADDED THIS     
            table = new JTable(sorter);             //NEW
            sorter.setTableHeader(table.getTableHeader()); //ADDED THIS
            table.setPreferredScrollableViewportSize(new Dimension(500, 70));
            //Set up tool tips for column headers.
            table.getTableHeader().setToolTipText(
                    "Click to specify sorting; Control-Click to specify secondary sorting");
            //Create the scroll pane and add the table to it.
            JScrollPane scrollPane = new JScrollPane(table);
            //Add the scroll pane to this panel.
            superPanel.add("Center", scrollPane);
            superPanel.add("South",clickMe);
            clickMe.addActionListener(this);              
        public JPanel getPanel()
             return superPanel;
        public void init1()
             //in real life this will be done from the db
             Traveler a = new Traveler();
             Traveler b = new Traveler();
             Traveler c = new Traveler();
             a.setFirstName("Elvis");
             a.setLastName("Presley");
             a.setSprot("Ping Pong");
             a.setNumYears(3);
             a.setVegetarian(true);
             b.setFirstName("Elton");
             b.setLastName("John");
             b.setSprot("Soccer");
             b.setNumYears(2);
             b.setVegetarian(true);
             c.setFirstName("shaquille");
             c.setLastName("oneil");
             c.setSprot("Golf");
             c.setNumYears(22);
             c.setVegetarian(true);
             defaultListModel.addElement(a);
             defaultListModel.addElement(b);
             defaultListModel.addElement(c);
        public void init2()
             //in real life this will be done from the db
             Traveler d = new Traveler();
             Traveler e = new Traveler();
             Traveler f = new Traveler();
             Traveler g = new Traveler();
             d.setFirstName("John");
             d.setLastName("Smith");
             d.setSprot("Tennis");
             d.setNumYears(32);
             d.setVegetarian(true);
             e.setFirstName("Ron");
             e.setLastName("Cohen");
             e.setSprot("Baseball");
             e.setNumYears(12);
             e.setVegetarian(true);
             f.setFirstName("Donald");
             f.setLastName("Mac Novice");
             f.setSprot("Vallyball");
             f.setNumYears(1);
             f.setVegetarian(true);
             g.setFirstName("Eithan");
             g.setLastName("Superstar");
             g.setSprot("Vallyball");
             g.setNumYears(21);
             g.setVegetarian(true);
             defaultListModel.addElement(d);
             defaultListModel.addElement(e);
             defaultListModel.addElement(f);
             defaultListModel.addElement(g);            
        class MyTableModel extends AbstractTableModel
             private DefaultListModel myModel;
             public MyTableModel(DefaultListModel m)
                  myModel=m;
            private String[] columnNames = {"First Name",
                                            "Last Name",
                                            "Sport",
                                            "# of Years",
                                            "Vegetarian"};
            public int getColumnCount()
                return columnNames.length;
            public int getRowCount()
                return myModel.size();
            public String getColumnName(int column)
                 return getNames()[column];             
             public String[] getNames()
                  String[] names = {"First Name", "Last Name", "Sport", "# of Years", "Vegetarian"};
                  return names;
            public Object getValueAt(int row, int col)
                 return distributeObjectsInTable(row, col, (Traveler) myModel.elementAt(row));
            public Object distributeObjectsInTable(int row, int col, Traveler tr)
               switch(col)
                         case 0:
                              return tr.getFirstName();
                         case 1:
                           return tr.getLastName();
                      case 2:
                           return tr.getSprot();
                      case 3:
                           return new Integer(tr.getNumYears());
                      case 4:
                           return new Boolean (tr.isVegetarian());
                     default:
                         return "Error";
            public Class getColumnClass(int c)
                return getValueAt(0, c).getClass();
        private static void createAndShowGUI()
            //Make sure we have nice window decorations.
            JFrame.setDefaultLookAndFeelDecorated(true);
            //Create and set up the window.
            JFrame frame = new JFrame("TableSorterDemo");
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            //Create and set up the content pane.
            TableSorterDemo newContentPane = new TableSorterDemo();
            newContentPane.getPanel().setOpaque(true); //content panes must be opaque
            frame.setContentPane(newContentPane.getPanel());
            //Display the window.
            frame.pack();
            frame.setVisible(true);
        public static void main(String[] args)
            //Schedule a job for the event-dispatching thread:
            //creating and showing this application's GUI.
            javax.swing.SwingUtilities.invokeLater(new Runnable()                   
                public void run()
                    createAndShowGUI();
         public void actionPerformed(ActionEvent ae)
              if (ae.getSource()==clickMe)
                   defaultListModel.removeAllElements();
                   init2(); //if the size of the model was less than 2 items - the result will be ok.
                              //in other words, if you commens the last 2 rows of this method (addElement(f) & g)
                             // the result will be fine.
                   table.updateUI();          
    }//(2) Traveler
    package sorter;
    public class Traveler
         private String firstName;
         private String lastName;
         private String sprot;
         private int numYears;
         private boolean vegetarian;
         public String getFirstName()
              return firstName;
         public String getLastName()
              return lastName;
         public int getNumYears()
              return numYears;
         public String getSprot()
              return sprot;
         public boolean isVegetarian()
              return vegetarian;
         public void setFirstName(String firstName)
              this.firstName = firstName;
         public void setLastName(String lastName)
              this.lastName = lastName;
         public void setNumYears(int numYears)
              this.numYears = numYears;
         public void setSprot(String sprot)
              this.sprot = sprot;
         public void setVegetarian(boolean vegetarian)
              this.vegetarian = vegetarian;
    }//(3)TableSorter
    package sorter;
    import java.awt.*;
    import java.awt.event.*;
    import java.util.*;
    import java.util.List;
    import javax.swing.*;
    import javax.swing.event.TableModelEvent;
    import javax.swing.event.TableModelListener;
    import javax.swing.table.*;
    public class TableSorter extends AbstractTableModel {
        protected TableModel tableModel;
        public static final int DESCENDING = -1;
        public static final int NOT_SORTED = 0;
        public static final int ASCENDING = 1;
        private static Directive EMPTY_DIRECTIVE = new Directive(-1, NOT_SORTED);
        public static final Comparator COMPARABLE_COMAPRATOR = new Comparator() {
            public int compare(Object o1, Object o2) {
                return ((Comparable) o1).compareTo(o2);
        public static final Comparator LEXICAL_COMPARATOR = new Comparator() {
            public int compare(Object o1, Object o2) {
                return o1.toString().compareTo(o2.toString());
        private Row[] viewToModel;
        private int[] modelToView;
        private JTableHeader tableHeader;
        private MouseListener mouseListener;
        private TableModelListener tableModelListener;
        private Map columnComparators = new HashMap();
        private List sortingColumns = new ArrayList();
        public TableSorter() {
            this.mouseListener = new MouseHandler();
            this.tableModelListener = new TableModelHandler();
        public TableSorter(TableModel tableModel) {
            this();
            setTableModel(tableModel);
        public TableSorter(TableModel tableModel, JTableHeader tableHeader) {
            this();
            setTableHeader(tableHeader);
            setTableModel(tableModel);
        private void clearSortingState() {
            viewToModel = null;
            modelToView = null;
        public TableModel getTableModel() {
            return tableModel;
        public void setTableModel(TableModel tableModel) {
            if (this.tableModel != null) {
                this.tableModel.removeTableModelListener(tableModelListener);
            this.tableModel = tableModel;
            if (this.tableModel != null) {
                this.tableModel.addTableModelListener(tableModelListener);
            clearSortingState();
            fireTableStructureChanged();
        public JTableHeader getTableHeader() {
            return tableHeader;
        public void setTableHeader(JTableHeader tableHeader) {
            if (this.tableHeader != null) {
                this.tableHeader.removeMouseListener(mouseListener);
                TableCellRenderer defaultRenderer = this.tableHeader.getDefaultRenderer();
                if (defaultRenderer instanceof SortableHeaderRenderer) {
                    this.tableHeader.setDefaultRenderer(((SortableHeaderRenderer) defaultRenderer).tableCellRenderer);
            this.tableHeader = tableHeader;
            if (this.tableHeader != null) {
                this.tableHeader.addMouseListener(mouseListener);
                this.tableHeader.setDefaultRenderer(
                        new SortableHeaderRenderer(this.tableHeader.getDefaultRenderer()));
        public boolean isSorting() {
            return sortingColumns.size() != 0;
        private Directive getDirective(int column) {
            for (int i = 0; i < sortingColumns.size(); i++) {
                Directive directive = (Directive)sortingColumns.get(i);
                if (directive.column == column) {
                    return directive;
            return EMPTY_DIRECTIVE;
        public int getSortingStatus(int column) {
            return getDirective(column).direction;
        private void sortingStatusChanged() {
            clearSortingState();
            fireTableDataChanged();
            if (tableHeader != null) {
                tableHeader.repaint();
        public void setSortingStatus(int column, int status) {
            Directive directive = getDirective(column);
            if (directive != EMPTY_DIRECTIVE) {
                sortingColumns.remove(directive);
            if (status != NOT_SORTED) {
                sortingColumns.add(new Directive(column, status));
            sortingStatusChanged();
        protected Icon getHeaderRendererIcon(int column, int size) {
            Directive directive = getDirective(column);
            if (directive == EMPTY_DIRECTIVE) {
                return null;
            return new Arrow(directive.direction == DESCENDING, size, sortingColumns.indexOf(directive));
        private void cancelSorting() {
            sortingColumns.clear();
            sortingStatusChanged();
        public void setColumnComparator(Class type, Comparator comparator) {
            if (comparator == null) {
                columnComparators.remove(type);
            } else {
                columnComparators.put(type, comparator);
        protected Comparator getComparator(int column) {
            Class columnType = tableModel.getColumnClass(column);
            Comparator comparator = (Comparator) columnComparators.get(columnType);
            if (comparator != null) {
                return comparator;
            if (Comparable.class.isAssignableFrom(columnType)) {
                return COMPARABLE_COMAPRATOR;
            return LEXICAL_COMPARATOR;
        private Row[] getViewToModel() {
            if (viewToModel == null) {
                int tableModelRowCount = tableModel.getRowCount();
                viewToModel = new Row[tableModelRowCount];
                for (int row = 0; row < tableModelRowCount; row++) {
                    viewToModel[row] = new Row(row);
                if (isSorting()) {
                    Arrays.sort(viewToModel);
            return viewToModel;
        public int modelIndex(int viewIndex)
            return getViewToModel()[viewIndex].modelIndex;
        private int[] getModelToView()
            if (modelToView == null) {
                int n = getViewToModel().length;
                modelToView = new int[n];
                for (int i = 0; i < n; i++) {
                    modelToView[modelIndex(i)] = i;
            return modelToView;
        // TableModel interface methods
        public int getRowCount() {
            return (tableModel == null) ? 0 : tableModel.getRowCount();
        public int getColumnCount() {
            return (tableModel == null) ? 0 : tableModel.getColumnCount();
        public String getColumnName(int column) {
            return tableModel.getColumnName(column);
        public Class getColumnClass(int column) {
            return tableModel.getColumnClass(column);
        public boolean isCellEditable(int row, int column) {
            return tableModel.isCellEditable(modelIndex(row), column);
        public Object getValueAt(int row, int column) {
            return tableModel.getValueAt(modelIndex(row), column);
        public void setValueAt(Object aValue, int row, int column) {
            tableModel.setValueAt(aValue, modelIndex(row), column);
        // Helper classes
        private class Row implements Comparable {
            private int modelIndex;
            public Row(int index) {
                this.modelIndex = index;
            public int compareTo(Object o) {
                int row1 = modelIndex;
                int row2 = ((Row) o).modelIndex;
                for (Iterator it = sortingColumns.iterator(); it.hasNext();) {
                    Directive directive = (Directive) it.next();
                    int column = directive.column;
                    Object o1 = tableModel.getValueAt(row1, column);
                    Object o2 = tableModel.getValueAt(row2, column);
                    int comparison = 0;
                    // Define null less than everything, except null.
                    if (o1 == null && o2 == null) {
                        comparison = 0;
                    } else if (o1 == null) {
                        comparison = -1;
                    } else if (o2 == null) {
                        comparison = 1;
                    } else {
                        comparison = getComparator(column).compare(o1, o2);
                    if (comparison != 0) {
                        return directive.direction == DESCENDING ? -comparison : comparison;
                return 0;
        private class TableModelHandler implements TableModelListener {
            public void tableChanged(TableModelEvent e) {
                // If we're not sorting by anything, just pass the event along.            
                if (!isSorting()) {
                    clearSortingState();
                    fireTableChanged(e);
                    return;
                // If the table structure has changed, cancel the sorting; the            
                // sorting columns may have been either moved or deleted from            
                // the model.
                if (e.getFirstRow() == TableModelEvent.HEADER_ROW) {
                    cancelSorting();
                    fireTableChanged(e);
                    return;
                // We can map a cell event through to the view without widening            
                // when the following conditions apply:
                // a) all the changes are on one row (e.getFirstRow() == e.getLastRow()) and,
                // b) all the changes are in one column (column != TableModelEvent.ALL_COLUMNS) and,
                // c) we are not sorting on that column (getSortingStatus(column) == NOT_SORTED) and,
                // d) a reverse lookup will not trigger a sort (modelToView != null)
                // Note: INSERT and DELETE events fail this test as they have column == ALL_COLUMNS.
                // The last check, for (modelToView != null) is to see if modelToView
                // is already allocated. If we don't do this check; sorting can become
                // a performance bottleneck for applications where cells 
                // change rapidly in different parts of the table. If cells
                // change alternately in the sorting column and then outside of            
                // it this class can end up re-sorting on alternate cell updates -
                // which can be a performance problem for large tables. The last
                // clause avoids this problem.
                int column = e.getColumn();
                if (e.getFirstRow() == e.getLastRow()
                        && column != TableModelEvent.ALL_COLUMNS
                        && getSortingStatus(column) == NOT_SORTED
                        && modelToView != null) {
                    int viewIndex = getModelToView()[e.getFirstRow()];
                    fireTableChanged(new TableModelEvent(TableSorter.this,
                                                         viewIndex, viewIndex,
                                                         column, e.getType()));
                    return;
                // Something has happened to the data that may have invalidated the row order.
                clearSortingState();
                fireTableDataChanged();
                return;
        private class MouseHandler extends MouseAdapter {
            public void mouseClicked(MouseEvent e) {
                JTableHeader h = (JTableHeader) e.getSource();
                TableColumnModel columnModel = h.getColumnModel();
                int viewColumn = columnModel.getColumnIndexAtX(e.getX());
                int column = columnModel.getColumn(viewColumn).getModelIndex();
                if (column != -1) {
                    int status = getSortingStatus(column);
                    if (!e.isControlDown()) {
                        cancelSorting();
                    // Cycle the sorting states through {NOT_SORTED, ASCENDING, DESCENDING} or
                    // {NOT_SORTED, DESCENDING, ASCENDING} depending on whether shift is pressed.
                    status = status + (e.isShiftDown() ? -1 : 1);
                    status = (status + 4) % 3 - 1; // signed mod, returning {-1, 0, 1}
                    setSortingStatus(column, status);
        private static class Arrow implements Icon {
            private boolean descending;
            private int size;
            private int priority;
            public Arrow(boolean descending, int size, int priority) {
                this.descending = descending;
                this.size = size;
                this.priority = priority;
            public void paintIcon(Component c, Graphics g, int x, int y) {
                Color color = c == null ? Color.GRAY : c.getBackground();            
                // In a compound sort, make each succesive triangle 20%
                // smaller than the previous one.
                int dx = (int)(size/2*Math.pow(0.8, priority));
                int dy = descending ? dx : -dx;
                // Align icon (roughly) with font baseline.
                y = y + 5*size/6 + (descending ? -dy : 0);
                int shift = descending ? 1 : -1;
                g.translate(x, y);
                // Right diagonal.
                g.setColor(color.darker());
                g.drawLine(dx / 2, dy, 0, 0);
                g.drawLine(dx / 2, dy + shift, 0, shift);
                // Left diagonal.
                g.setColor(color.brighter());
                g.drawLine(dx / 2, dy, dx, 0);
                g.drawLine(dx / 2, dy + shift, dx, shift);
                // Horizontal line.
                if (descending) {
                    g.setColor(color.darker().darker());
                } else {
                    g.setColor(color.brighter().brighter());
                g.drawLine(dx, 0, 0, 0);
                g.setColor(color);
                g.translate(-x, -y);
            public int getIconWidth() {
                return size;
            public int getIconHeight() {
                return size;
        private class SortableHeaderRenderer implements TableCellRenderer {
            private TableCellRenderer tableCellRenderer;
            public SortableHeaderRenderer(TableCellRenderer tableCellRenderer) {
                this.tableCellRenderer = tableCellRenderer;
            public Component getTableCellRendererComponent(JTable table,
                                                           Object value,
                                                           boolean isSelected,
                                                           boolean hasFocus,
                                                           int row,
                                                           int column) {
                Component c = tableCellRenderer.getTableCellRendererComponent(table,
                        value, isSelected, hasFocus, row, column);
                if (c instanceof JLabel) {
                    JLabel l = (JLabel) c;
                    l.setHorizontalTextPosition(JLabel.LEFT);
                    int modelColumn = table.convertColumnIndexToModel(column);
                    l.setIcon(getHeaderRendererIcon(modelColumn, l.getFont().getSize()));
                return c;
        private static class Directive {
            private int column;
            private int direction;
            public Directive(int column, int direction) {
                this.column = column;
                this.direction = direction;
    }

    The table listens to the TableModel for changes. Changing the table by adding/removing
    rows or columns has no affect on its table model. If you make changes to the table model
    the table will be notified by its TableModelListener and change its view. So tell
    MyTableModel about the change of data:
    public class TableSorterDemo implements ActionListener
        MyTableModel tableModel;
        public TableSorterDemo()
            defaultListModel = new DefaultListModel();
            init1();
            tableModel = new MyTableModel(defaultListModel);
            TableSorter sorter = new TableSorter(tableModel);
        public void actionPerformed(ActionEvent ae)
            if (ae.getSource()==clickMe)
                defaultListModel.removeAllElements();
                init2();
                tableModel.fireTableStructureChanged();
    }

Maybe you are looking for

  • How to put in put fields in abap objects using HTML documents

    Hallo Every body, I have got a problem in my program actually I have created 4 splitters. in this two are for Document search and the other two are for material search, The other two splitters are for HTML. I wanted to give the end user five i in put

  • MS Word. Can't view normal window size of saved docs.

    I have  Microsoft Word 2008 for Mac. (running Mavericks on my MacBookAir)  Recently, when I create a document and save it to Docs or Desktop I have problems viewing it later.  When I re-open it I only get a very reduced size window in upper left corn

  • HTC ONE in black (Stock)

    does anyone know when the black htc one will be in bestbuy stores? i just purchased the silver and i like it but the black just looks so much more sleeker and i really want that one but the employees at my local store dont know. so i figured i would

  • Sync RFC scenario

    Hi, I need a synchronous RFC scenario. My requirement si jsut to run a UDF in mapping and give teh response back to RFC. What can be the best reciever side which gives the response back to RFC. Remrmber, I just need to call a mapping. File is not pos

  • Integration of CO with PP

    Hi Friends, Can any please give me the detailed integration part of Controlling with Production Planning and accounting entries. With thousands of thanks in advance, Regards, Kalpana.