/*
 * $Id: GroupListForm.java,v 1.28 2006/05/28 18:10:54 marbobo Exp $
 *
 * Copyright (c) Siemens AG 2008 
 *           (c) Universität Paderborn 2008 
 * Licensed under EUPL 1.1. 
 *
 * $Log: GroupListForm.java,v $
 * Revision 1.28  2006/05/28 18:10:54  marbobo
 * + Benutzer- und Gruppensuche nach Umlauten nochmals verbessert
 *
 * Revision 1.27  2006/04/29 18:39:47  marbobo
 * + Refactoriengs und eine Ausgaben vereinheitlicht
 *
 * Revision 1.26  2006/02/27 16:16:18  marbobo
 * + Systemsichten hinzugefügt
 * + SysLinks angepasst
 * + Benutzer können falls gewünscht Dokumentqueries anlegen
 *
 * Revision 1.25  2005/09/15 23:16:42  marbobo
 * + Sprachabhängiges Sortieren implementiert
 *
 * Revision 1.24  2005/02/20 16:57:27  marbobo
 * + Beim Speichern der Entities in die Datenbank wird sichergestellt
 *    dass Unicode-Zeichen in Kodierterform (als &#xxxxx;) gespeichert werden
 *
 * Revision 1.23  2005/02/16 23:00:31  marbobo
 * + Suche auf Unicode-Zeichen erweitert
 *
 * Revision 1.22  2005/02/15 09:26:52  bigmac
 * Refactorings
 *
 * Revision 1.21  2005/01/20 11:20:08  bigmac
 * getHelpText() entfernt
 *
 * Revision 1.20  2004/11/14 21:37:18  marbobo
 * + getHelpText()
 *
 * Revision 1.19  2004/11/13 20:44:22  marbobo
 * + Bugfix bei der Gruppensuche ( Betrifft die Literal Behandlung )
 *
 * Revision 1.18  2004/11/12 18:45:19  marbobo
 * + Bugfix
 *
 * Revision 1.17  2004/11/12 00:26:34  marbobo
 * + Suche nach Gruppen implementiert
 *
 * Revision 1.16  2004/09/01 12:35:40  marbobo
 * + Bugfix
 *
 * Revision 1.15  2004/08/30 20:06:35  marbobo
 * + Verbesserung des Redirectmechanismus
 *
 * Revision 1.14  2004/08/19 14:09:01  marbobo
 * + Sortierung für Kontostatus angepasst
 *
 * Revision 1.13  2004/08/12 21:41:24  marbobo
 * + Actions auf Requestparameter umgestellt
 * + Bugfixes und Quellcode maintenance
 *
 * Revision 1.12  2004/07/26 12:29:17  marbobo
 * + Sortierung nach Anzahl-Benutzer
 *
 * Revision 1.11  2004/07/20 08:09:56  jonyp
 * added copyright info + cvs log
 *
 *
 */
package vkc.administration.form;

import java.text.CollationKey;
import java.text.Collator;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Comparator;
import java.util.HashMap;
import java.util.List;

import javax.servlet.http.HttpServletRequest;

import org.apache.struts.action.ActionMapping;

import vkc.db.serializer.VKCGroupSerializer;
import vkc.db.serializer.VKCUserSerializer;
import vkc.exception.DBException;
import vkc.util.StringUtils;
import vkc.util.VKCStringUtils;
import vkc.view.bean.GroupInfo;
import vkc.view.bean.GroupInfoRange;
import vkc.view.bean.UserInfo;
import vkc.view.form.BasicActionForm;

public final class GroupListForm extends BasicActionForm {
	public final static int SORT_NAME_UP    			= 1;
	public final static int SORT_NAME_DOWN  			= 2;

	public final static int SORT_DESCRIPTION_UP   		= 3;
	public final static int SORT_DESCRIPTION_DOWN 		= 4;

	public final static int SORT_ACCOUNTSTATUS_UP  		= 5;
	public final static int SORT_ACCOUNTSTATUS_DOWN		= 6;
	
	public final static int SORT_CREATOR_UP  			= 7;
	public final static int SORT_CREATOR_DOWN 			= 8;

	public final static int SORT_CREATED_UP  			= 9;
	public final static int SORT_CREATED_DOWN 			= 10;

	public final static int SORT_COUNTMEMBERS_UP		= 11;
	public final static int SORT_COUNTMEMBERS_DOWN 		= 12;

	private GroupInfo[]	groupInfos	= null;

	private HashMap	ranges	= new HashMap();
	
    private Integer allGroupsCount	= new Integer(0);
	private Integer groupsPerPage	= new Integer(10);
	private Integer listIndex    	= new Integer(0);
	private Integer sortMode     	= new Integer(SORT_NAME_UP);
	
	private Integer[] selectedIds	= new Integer[0];

    private String searchQuery 			= "";
	private String selectedCmdAction	= "noaction";

	public void reset(ActionMapping mapping, HttpServletRequest request) {
		super.reset(mapping, request);
	    
	    groupInfos = null;
	    sortMode = new Integer(SORT_NAME_UP);
		selectedCmdAction = "noaction";
	}

	public GroupInfo[] getGroupInfos() throws DBException {
		if (groupInfos == null) {
		    groupInfos = new GroupInfo[0];
    		setAllGroupsCount(new Integer(0));

    		if (getUser().hasAdminPrivileges()) {
        		setAllGroupsCount(new Integer(VKCGroupSerializer.getAllGroupsCount()));

        		if (getAllGroupsCount().intValue() > 0) {
            		if (!isEmpty(getSearchQuery())) {
                    	String[] xqueries = getDatabaseXmlEntityQueries();
                    	String[] queries = new String[1 + xqueries.length];
                    	queries[0] = getDatabaseQuery();
                    	
                    	for (int i = 0; i < xqueries.length; i++) {
							queries[i + 1] = xqueries[i];
						}
                    	
            		    groupInfos = (GroupInfo[])VKCGroupSerializer.retrieveGroupInfosByQueries(queries).toArray(new GroupInfo[0]);
        		    } else {
        		        groupInfos = (GroupInfo[])VKCGroupSerializer.retrieveGroupInfos().toArray(new GroupInfo[0]);
        		    }
        		}
    		} else if (getUser().isDedicatedGroupsAdmin()) {
        		setAllGroupsCount(new Integer(VKCGroupSerializer.getAllGroupsCountByCreator(getUser().getUserId())));

        		if (getAllGroupsCount().intValue() > 0) {
            		if (!isEmpty(getSearchQuery())) {
                    	String[] xqueries = getDatabaseXmlEntityQueries();
                    	String[] queries = new String[1 + xqueries.length];
                    	queries[0] = getDatabaseQuery();
                    	
                    	for (int i = 0; i < xqueries.length; i++) {
							queries[i + 1] = xqueries[i];
						}
                    	
            		    groupInfos = (GroupInfo[])VKCGroupSerializer.retrieveGroupInfosByCreatorAndQueries(getUser().getUserId(), queries).toArray(new GroupInfo[0]);
        		    } else {
        		        groupInfos = (GroupInfo[])VKCGroupSerializer.retrieveGroupInfosByCreator(getUser().getUserId()).toArray(new GroupInfo[0]);
        		    }
        		}
    		}
    	    
    		sort(groupInfos, getSortMode());
		}
		
		return groupInfos;
	}

	private void sort(GroupInfo[] groupInfos, Integer sortMode) throws DBException {
		int mode = sortMode.intValue();

		Comparator c = null;
		final Collator collator = Collator.getInstance(getUser().getLanguage().getLocale());

		if (mode == SORT_NAME_UP) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;
					
                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getName()));
                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getName()));
                	
                	return key1.compareTo(key2);
				}
			};
		} else if (mode == SORT_NAME_DOWN) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;
					
                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getName()));
                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getName()));
                	
                	return key2.compareTo(key1);
				}
			};
		} else if (mode == SORT_DESCRIPTION_UP) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;
					
                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getDescription()));
                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getDescription()));
                	
                	return key1.compareTo(key2);
				}
			};
		} else if (mode == SORT_DESCRIPTION_DOWN) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;
					
                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getDescription()));
                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getDescription()));
                	
                	return key2.compareTo(key1);
				}
			};
		} else if (mode == SORT_ACCOUNTSTATUS_UP) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;
					int g1Value = g1.isGroupValid() ? 1 : 0;
					int g2Value = g2.isGroupValid() ? 1 : 0;
					
					return g1Value > g2Value ? 1 : 0;
				}
			};
		} else if (mode == SORT_ACCOUNTSTATUS_DOWN) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;
					int g1Value = g1.isGroupValid() ? 1 : 0;
					int g2Value = g2.isGroupValid() ? 1 : 0;
					
					return g1Value < g2Value ? 1 : 0;
				}
			};
		} else if (mode == SORT_CREATOR_UP) {
			final HashMap groups = getAllUserInfos();
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;
					String k1 = g1.getCreatorId() == null ? "" : g1.getCreatorId().toString();
					String k2 = g2.getCreatorId() == null ? "" : g2.getCreatorId().toString();
					UserInfo c1 = (UserInfo)groups.get(k1);
					UserInfo c2 = (UserInfo)groups.get(k2);
			
					if (c1 == null && c2 == null) {
	                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getName()));
	                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getName()));
	                	
	                	return key1.compareTo(key2);
					}
			
					if (c1 == null) {
						return -1;
					}

					if (c2 == null) {
						return 1;
					}
			
                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(c1.getUsername()));
                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(c2.getUsername()));
                	
                	return key1.compareTo(key2);
				}
			};
		} else if (mode == SORT_CREATOR_DOWN) {
			final HashMap users = getAllUserInfos();
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;
					String k1 = g1.getCreatorId() == null ? "" : g1.getCreatorId().toString();
					String k2 = g2.getCreatorId() == null ? "" : g2.getCreatorId().toString();
					UserInfo c1 = (UserInfo)users.get(k1);
					UserInfo c2 = (UserInfo)users.get(k2);
			
					if (c1 == null && c2 == null) {
	                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getName()));
	                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getName()));
	                	
	                	return key2.compareTo(key1);
					}
			
					if (c1 == null) {
						return 1;
					}

					if (c2 == null) {
						return -1;
					}
			
                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(c1.getUsername()));
                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(c2.getUsername()));
                	
                	return key2.compareTo(key1);
				}
			};
		} else if (mode == SORT_CREATED_UP) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;

					if (g1.getCreated() == null && g2.getCreated() == null) {
	                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getName()));
	                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getName()));
	                	
	                	return key1.compareTo(key2);
					}
					
					if (g1.getCreated() == null) {
						return -1;
					}

					if (g2.getCreated() == null) {
						return 1;
					}
					
					return g1.getCreated().after(g2.getCreated()) ? 1 : 0;
				}
			};
		} else if (mode == SORT_CREATED_DOWN) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;

					if (g1.getCreated() == null && g2.getCreated() == null) {
	                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getName()));
	                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getName()));
	                	
	                	return key2.compareTo(key1);
					}
					
					if (g1.getCreated() == null) {
						return 1;
					}

					if (g2.getCreated() == null) {
						return -1;
					}
					
					return g1.getCreated().before(g2.getCreated()) ? 1 : 0;
				}
			};
		} else if (mode == SORT_COUNTMEMBERS_UP) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;

					if (g1.getCountMembers() == g2.getCountMembers()) {
	                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getName()));
	                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getName()));
	                	
	                	return key1.compareTo(key2);
					}

					return g1.getCountMembers() > g2.getCountMembers() ? 1 : 0;
				}
			};
		} else if (mode == SORT_COUNTMEMBERS_DOWN) {
			c = new Comparator() {
				public int compare(Object o1, Object o2) {
					GroupInfo g1 = (GroupInfo)o1;
					GroupInfo g2 = (GroupInfo)o2;

					if (g1.getCountMembers() == g2.getCountMembers()) {
	                	CollationKey key1 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g1.getName()));
	                	CollationKey key2 = collator.getCollationKey(VKCStringUtils.decodeXmlEntities(g2.getName()));
	                	
	                	return key2.compareTo(key1);
					}

					return g1.getCountMembers() < g2.getCountMembers() ? 1 : 0;
				}
			};
		}

		Arrays.sort(groupInfos, c);
	}

	private HashMap getAllUserInfos() throws DBException {
		HashMap users = new HashMap();
		List userInfos = VKCUserSerializer.retrieveUserInfos();
		
		for (int i = 0; i < userInfos.size(); i++) {
			UserInfo u = (UserInfo)userInfos.get(i);
			users.put(u.getUserId().toString(), u);
		}

		return users;
	}

	public void setGroupInfos(GroupInfo[] infos) {
		groupInfos = infos;
	}

    public Integer getAllGroupsCount() {
        return allGroupsCount;
    }
	
    public void setAllGroupsCount(Integer i) {
        allGroupsCount = i;
    }
    
	public Integer getSortMode() {
		return sortMode;
	}

	public void setSortMode(Integer i) {
		sortMode = i;
	}

	public Integer getGroupsPerPage() {
		return groupsPerPage;
	}

	public void setGroupsPerPage(Integer i) {
		groupsPerPage = i;
	}

	public Integer getNumberOfGroupInfos() throws DBException {
		return new Integer(getGroupInfos().length);
	}

	public Integer getGroupInfoPageCount() throws DBException {
		double pageCount = getGroupInfos().length;
		pageCount = pageCount / getGroupsPerPage().intValue();
		pageCount = Math.ceil(pageCount);

		return new Integer((int)pageCount);
	}

	public Integer[] getPageIndices() throws DBException {
		ArrayList list = new ArrayList();
		ranges.clear();

		for (int i = 0; i < getGroupInfoPageCount().intValue(); i++) {
			Integer index = new Integer(i * getGroupsPerPage().intValue());
			ranges.put(index, getVisibleGroupInfoRanges(index));
			list.add(index);
		}
		
		return (Integer[])list.toArray(new Integer[list.size()]);
	}

	public Integer getListIndex() {
		return listIndex;
	}

	public void setListIndex(Integer i) {
		listIndex = i;
	}

	public Integer[] getSelectedIds() {
		return selectedIds;
	}

	public void setSelectedIds(Integer[] integers) {
		if (integers == null) {
			selectedIds = new Integer[0];
		} else {
			selectedIds = integers;
		}
	}
    
	public GroupInfo[] getVisibleGroupInfos() throws DBException {
		int length = getGroupsPerPage().intValue();
		
		if (getListIndex().intValue() + getGroupsPerPage().intValue() > getGroupInfos().length) {
			length = getGroupInfos().length % getGroupsPerPage().intValue();
		}

		GroupInfo[] visibleGroupInfos = new GroupInfo[length];
		
		if (getGroupInfos().length > 0) {
		    int sourcepos = getListIndex().intValue();
		    
		    if (sourcepos > getGroupInfos().length) {
		        sourcepos = 0;
		        setListIndex(new Integer(0));
		    }
		    
			System.arraycopy(getGroupInfos(), sourcepos, visibleGroupInfos, 0, length);
		}

		return visibleGroupInfos;
	}
    
    public Integer getVisibleGroupInfoSizes() throws DBException {
    	return new Integer(getVisibleGroupInfos().length);
    }
    
	public GroupInfoRange getVisibleGroupInfoRanges(Integer pageIndex) throws DBException {
		int fromIndex = pageIndex.intValue();
		int toIndex = fromIndex + (getGroupsPerPage().intValue() - 1);
		GroupInfo[] groupInfos = getGroupInfos();
		int endIndex = (groupInfos.length % getGroupsPerPage().intValue()) - 1;
		
		if (toIndex >= groupInfos.length) {
		    toIndex = fromIndex + endIndex;
		}
		
		GroupInfo fromGroup = groupInfos[fromIndex];
		GroupInfo toGroup = groupInfos[toIndex];
		
		return new GroupInfoRange(fromGroup, toGroup);
	}
	
	public Object getRangeValue(String key) {
		return ranges.get(Integer.valueOf(key));
	}

	public String getSelectedCmdAction() {
		return selectedCmdAction;
	}

	public void setSelectedCmdAction(String s) {
		selectedCmdAction = s;
	}

	public String getSearchQuery() {
	    return searchQuery;
	}
	
	public void setSearchQuery(String s) {
	    searchQuery = StringUtils.normalize(s);
	}
	
	private String getDatabaseQuery() {
	    if (isEmpty(getSearchQuery())) {
	        return "";
	    }
	    
        String query = VKCStringUtils.filterUnicodeChars(clearAloneEscapeChars(getSearchQuery()));
        query = StringUtils.replaceToken(query, "%", "\\%");
        query = StringUtils.replaceToken(query, "_", "\\_");
        query = replaceLiterals(query, "*", "%");
        query = replaceLiterals(query, "?", "_");
        query = replaceLiterals(query, "\\*", "*");
        query = replaceLiterals(query, "\\?", "?");

        return query;
	}
	
    private String[] getDatabaseXmlEntityQueries() {
        if (isEmpty(getSearchQuery())) {
            return new String[] {};
        }

        String queries[] = new String[5];
        String query = VKCStringUtils.filterUnicodeChars(clearAloneEscapeChars(getSearchQuery()));
        query = StringUtils.replaceToken(query, "%", "\\%");
        query = StringUtils.replaceToken(query, "_", "\\_");
        query = replaceLiterals(query, "*", "%");
        
        for (int i = 0; i < queries.length; i++) {
            String replacement = "&#";
            
            for (int j = 0; j < i + 1; j++) {
				replacement += "_";
			}
            
            replacement += ";";
        	queries[i] = replaceLiterals(query, "?", replacement);
            queries[i] = replaceLiterals(queries[i], "\\*", "*");
            queries[i] = replaceLiterals(queries[i], "\\?", "?");
            queries[i] = queries[i];
		}

        return queries;
    }

	private String clearAloneEscapeChars(String str) {
	    StringBuffer sb = new StringBuffer();
        int index = 0;

        while (true) {
            index = str.indexOf("\\");

            if (index < 0) {
                break;
            }
            
            if (str.startsWith("*", index + 1) || str.startsWith("?", index + 1) || str.startsWith("\\", index + 1)) {
                sb.append(str.substring(0, index + 2));
                str = str.substring(index + 2);
            } else {
                sb.append(str.substring(0, index));
                str = str.substring(index + 1);
            }
        }

        return sb.toString() + str;
	}
	
	private String replaceLiterals(String str, String literal, String replacement) {
	    StringBuffer sb = new StringBuffer();
        int index = 0;

        while (true) {
            index = str.indexOf(literal);

            if (index < 0) {
                break;
            }
            
            int escapeCount = 0;
            
            for (int i = index - 1; i >= 0; i--) {
                if (str.charAt(i) == '\\') {
                    escapeCount++;
                } else {
                    break;
                }
            }
            
            if (escapeCount % 2 == 1) {
                sb.append(str.substring(0, index + literal.length()));
            } else {
                sb.append(str.substring(0, index));
                sb.append(replacement);
            }

            str = str.substring(index + literal.length());
        }

        return sb.toString() + str;
	}
	
	public String getEditGroupLink() {
	    String currentLink = "/groupList.do?";
	    currentLink += "action.search.redirect=true";
	    currentLink += "&listIndex=" + getListIndex();
	    currentLink += "&sortMode=" + getSortMode();
	    currentLink += "&groupsPerPage=" + getGroupsPerPage();
	    currentLink += "&searchQuery=" + VKCStringUtils.base64Encode(getSearchQuery());

	    return "/editGroup.do?initialize=true&redirect=" + VKCStringUtils.base64Encode(currentLink);
	}

	public boolean getSortByName() {
		return 
			getSortMode().intValue() == GroupListForm.SORT_NAME_UP || 
			getSortMode().intValue() == GroupListForm.SORT_NAME_DOWN;
	}

	public boolean getSortByDescription() {
		return 
			getSortMode().intValue() == GroupListForm.SORT_DESCRIPTION_UP || 
			getSortMode().intValue() == GroupListForm.SORT_DESCRIPTION_DOWN;
	}

	public boolean getSortByAccountStatus() {
		return 
			getSortMode().intValue() == GroupListForm.SORT_ACCOUNTSTATUS_UP ||
			getSortMode().intValue() == GroupListForm.SORT_ACCOUNTSTATUS_DOWN;
	}
	
	public boolean getSortByCreator() {
		return 
			getSortMode().intValue() == GroupListForm.SORT_CREATOR_DOWN || 
			getSortMode().intValue() == GroupListForm.SORT_CREATOR_UP;
	}

	public boolean getSortByCreated() {
		return 
			getSortMode().intValue() == GroupListForm.SORT_CREATED_DOWN || 
			getSortMode().intValue() == GroupListForm.SORT_CREATED_UP;
	}
	
	public boolean getSortByCountMembers() {
		return 
			getSortMode().intValue() == GroupListForm.SORT_COUNTMEMBERS_DOWN || 
			getSortMode().intValue() == GroupListForm.SORT_COUNTMEMBERS_UP;
	}
}