on 12-19-2007 9:29 AM
Hello Friends,
I have following senario. I need to show a dialog with table, and I am trying to implement a table filter on this popup table.
I have two modle nodes, which are binded via controller, and the issue is when it filters once, the values are gone, means when I second time open the popup the table is still shows me the earlier filtred values....
So I thought that I need to bind only one modle node and use the copyservice method to copy the stuff, but this copyservicve method did not worked for me.... ( how I can manually copy the node to other context node ) ?
WDCopyService.copyElements(wdContext.nodeRFC_ShippingPartner_In().nodeOutput().nodeZmat_Fg(), wdContext.nodeCopy_Zmat_Fg());
I used following code to do filter:
package com.sonopress.util;
import java.util.Comparator;
import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
import java.util.StringTokenizer;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDAbstractDropDownByIndex;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDAbstractDropDownByKey;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDAbstractInputField;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDAbstractTableColumn;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDCaption;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDImage;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDLink;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDProgressIndicator;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDRadioButton;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDTable;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDTableCellEditor;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDTableColumn;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDTextEdit;
import com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDTextView;
import com.sap.tc.webdynpro.progmodel.api.IWDAction;
import com.sap.tc.webdynpro.progmodel.api.IWDCustomEvent;
import com.sap.tc.webdynpro.progmodel.api.IWDNode;
import com.sap.tc.webdynpro.progmodel.api.IWDNodeElement;
import com.sap.tc.webdynpro.progmodel.api.IWDViewElement;
import com.sap.tc.webdynpro.progmodel.api.WDCopyService;
/**
Helper class that makes a Web Dynpro table UI element filterable (column-wise).
*/
public final class TableFilter
{
/**
Creates a table filter for the given table using the given filter action.
This constructor must be called from <code>wdDoModifyView()</code>, but
usually only when that hook is called for the first time. Store the newly
created instance in a context attribute with Java native type
<code>com.sap.tc.webdynpro.tests.utils.TableFilter</code>.
The given filter action's event handler will be bound to the <code>onAction</code>
event of filter columns and must at least call this table filter's
<code>filter(wdEvent)</code> method.
*
When a table is made filterable its <code>onAction</code> event (incl.
parameter mapping) is changed. Furthermore if a header is present for that
column then the header's <code>imageSource</code> property is also changed
to indicate the currently filtered column.
*
@see filter()
@see com.sap.tc.webdynpro.clientserver.uielib.standard.api.IWDTable
*/
public TableFilter(IWDTable table, IWDAction filterAction)
{
this.table = table;
// sanity checks
if (filterAction == null)
throw new IllegalArgumentException("Filter action must be given");
if (table == null)
throw new IllegalArgumentException("Table must be given");
if (table.bindingOfDataSource() == null)
throw new IllegalArgumentException("Data source of table with id '" + table.getId() + "' must be bound");
String dataSourcePrefix = table.bindingOfDataSource() + ".";
int index = 0;
for (Iterator it = table.iterateGroupedColumns(); it.hasNext(); ++index)
{
// for every column: try to make it bindable
IWDTableColumn column = (IWDTableColumn) it.next();
// attribute must be determined
String bindingOfPrimaryProperty = bindingOfPrimaryProperty(column.getTableCellEditor());
if ( bindingOfPrimaryProperty == null
|| !bindingOfPrimaryProperty.startsWith(dataSourcePrefix) )
continue; // no attribute found or outside of data source
String attributeName = bindingOfPrimaryProperty.substring(dataSourcePrefix.length());
if (attributeName.indexOf('.') >= 0)
continue; // attribute not immediately below data source
table.setOnFilter(filterAction);
}
}
/**
This method must be called from the event handler of this table filter's
filter action. It performs the actual filter operation.
*/
public void filter(IWDCustomEvent wdEvent,IWDNode dataSource, IWDNode originalSource, IWDNode filterNode)
{
// find the things we need
String refinedFilter = null;
String field = null;
String attributeName = null;
String bindingOfPrimaryProperty = null;
String dataSourcePrefix = table.bindingOfDataSource() + ".";
// IWDTableColumn[] columns = table.getColumns();
IWDAbstractTableColumn[] columns = table.getGroupedColumns();
String path = null;
String attribute = null;
StringTokenizer tokenizer = null;
dataSource.invalidate();
WDCopyService.copyElements(originalSource,dataSource);
int totalElements = originalSource.size();
for(int i = totalElements - 1; i >= 0 ; i--)
{
IWDNodeElement element = dataSource.getElementAt(i);
for(int j =0; j < columns.length; j++ )
{
IWDTableColumn colmn = (IWDTableColumn)columns[j];
bindingOfPrimaryProperty = bindingOfPrimaryProperty(colmn.getTableCellEditor());
if(bindingOfPrimaryProperty != null
&& bindingOfPrimaryProperty.startsWith(dataSourcePrefix))
attributeName = bindingOfPrimaryProperty.substring(dataSourcePrefix.length());
if(attributeName.indexOf('.') < 0)
field = element.getAttributeAsText(attributeName);
if(colmn.bindingOfFilterValue() != null)
{
path = colmn.bindingOfFilterValue();
tokenizer = new StringTokenizer(path, ".");
while(tokenizer.hasMoreTokens())
{
attribute = tokenizer.nextToken();
}
refinedFilter = refineFilterString(filterNode.getCurrentElement().getAttributeAsText(attribute));
if(!(field.matches(refinedFilter)))
{
dataSource.removeElement(element);
}
else
{
// remove icon of previously filtered column
if ( currentlyFilteredColumn != null
&& currentlyFilteredColumn.getHeader() != null )
currentlyFilteredColumn.getHeader().setImageSource(null);
currentlyFilteredColumn = (IWDTableColumn)columns[j];
if ((currentlyFilteredColumn.getHeader() != null) && (dataSource.size() != originalSource.size()))
currentlyFilteredColumn.getHeader().setImageSource("~sapicons/s_b_filt.GIF");
}
}
}
}
}
/**
Returns the binding of the given table cell editor's property that is
considered "primary" or <code>null</code> if no such binding exists or no
such property can be determined.
*/
private static final String bindingOfPrimaryProperty(IWDTableCellEditor editor)
{
return editor instanceof IWDViewElement
? bindingOfPrimaryProperty((IWDViewElement) editor)
: null;
}
/**
Returns the binding of the given view element's property that is
considered "primary" or <code>null</code> if no such binding exists or no
such property can be determined.
*/
private static final String bindingOfPrimaryProperty(IWDViewElement element)
{
if (element instanceof IWDAbstractDropDownByIndex)
return ((IWDAbstractDropDownByIndex) element).bindingOfTexts();
if (element instanceof IWDAbstractDropDownByKey)
return ((IWDAbstractDropDownByKey) element).bindingOfSelectedKey();
if (element instanceof IWDAbstractInputField)
return ((IWDAbstractInputField) element).bindingOfValue();
if (element instanceof IWDCaption)
return ((IWDCaption) element).bindingOfText();
// if (element instanceof IWDCheckBox)
// return ((IWDCheckBox) element).bindingOfChecked();
if (element instanceof IWDLink)
return ((IWDLink) element).bindingOfText();
if (element instanceof IWDProgressIndicator)
return ((IWDProgressIndicator) element).bindingOfPercentValue();
if (element instanceof IWDRadioButton)
return ((IWDRadioButton) element).bindingOfSelectedKey();
if (element instanceof IWDTextEdit)
return ((IWDTextEdit) element).bindingOfValue();
if (element instanceof IWDTextView)
return ((IWDTextView) element).bindingOfText();
if (element instanceof IWDImage)
return ((IWDImage)element).bindingOfAlt();
return null;
}
/**
Instance of a comparator according to the ordering imposed by the
implementation of <code>Comparable</code>.
*/
private static final Comparator DEFAULT = new Comparator()
{
/**
Compares the given objects according to the ordering imposed by the first
ones <code>compareTo(Object)</code> function. Furthermore, <code>null</code>
is treated to be less than any object.
*
@see java.lang.Comparable#compareTo(java.lang.Object)
@see java.util.Comparator#compare(java.lang.Object, java.lang.Object)
*/
public int compare(Object o1, Object o2)
{
if (o1 == null && o2 == null)
return 0;
if (o1 == null)
return -1;
if (o2 == null)
return +1;
return ((Comparable) o1).compareTo((Comparable) o2);
}
};
/**
Map of table column to comparator (<code>ReversableComparator</code>)
used for sorting that column (sortable columns only).
*/
private final Map comparatorForColumn = new HashMap();
/**
Column that is currently sorted.
*/
private IWDTableColumn currentlyFilteredColumn;
/**
The table to be sorted.
*/
private final IWDTable table;
/**
Generic comparator that compares node elements by a given attribute with
the help of a given comparator.
*/
public final class NodeElementByAttributeComparator implements Comparator
{
/**
Creates a new comparator for the given attribute name that compares values
of that attribute according to the natural ordering of that attribute's
type (which must implement <code>java.lang.Comparable</code>).
*/
public NodeElementByAttributeComparator(String attributeName)
{
this(attributeName, null, false);
}
/**
Creates a new comparator for the given attribute name that compares values
of that attribute with the help of the given comparator. If no comparator
is given, the natural ordering of that attribute's type is used.
*/
public NodeElementByAttributeComparator(String attributeName, Comparator comparator)
{
this(attributeName, comparator, false);
}
/**
Creates a new comparator for the given attribute name that compares values
of that attribute either as objects (i.e. "in internal format") or as text
(i.e. "in external format") as indicated. The ordering is the natural
ordering of that attribute's type (which must implement
<code>java.lang.Comparable</code>) in case objects are compared or the
natural ordering of <code>java.lang.String</code> in case texts are compared.
*/
public NodeElementByAttributeComparator(String attributeName, boolean compareAsText)
{
this(attributeName, null, compareAsText);
}
/**
Internal constructor.
*/
private NodeElementByAttributeComparator(String attributeName,
Comparator comparator, boolean compareAsText)
{
if (attributeName == null)
throw new IllegalArgumentException("Attribute name must not be null");
if (comparator == null)
comparator = DEFAULT;
this.attributeName = attributeName;
this.comparator = comparator;
this.compareAsText = compareAsText;
}
/**
Compares the given objects which must be instances of <code>IWDNodeElement</code>
according to the values of the attribute given at construction time
with the help of the comparator given at construction time.
*
@see java.util.Comparator#compare(java.lang.Object, java.lang.Object)
@see com.sap.tc.webdynpro.progmodel.api.IWDNodeElement
*/
public int compare(Object o1, Object o2)
{
IWDNodeElement element1 = (IWDNodeElement) o1;
IWDNodeElement element2 = (IWDNodeElement) o2;
Object attributeValue1 = compareAsText
? element1.getAttributeAsText(attributeName)
: element1.getAttributeValue(attributeName);
Object attributeValue2 = compareAsText
? element2.getAttributeAsText(attributeName)
: element2.getAttributeValue(attributeName);
return comparator.compare(attributeValue1, attributeValue2);
}
/**
Name of the attribute used for comparisons.
*/
private final String attributeName;
/**
Comparator used for comparing the attribute's values.
*/
private final Comparator comparator;
/**
Indicates whether attribute values are compared as text (as opposed to
"as objects").
*/
private final boolean compareAsText;
}
/**
Comparator that knows how to reverse another comparator's sort direction.
*/
private final class ReversableComparator implements Comparator
{
/**
Creates a new reversable comparator for the given other comparator.
*/
public ReversableComparator(Comparator comparator)
{
if (comparator == null)
throw new IllegalArgumentException("Comparator must not be null");
this.comparator = comparator;
}
/**
@see java.util.Comparator#compare(java.lang.Object, java.lang.Object)
*/
public int compare(Object o1, Object o2)
{
return reversed
? -comparator.compare(o1, o2)
: comparator.compare(o1, o2);
}
/**
Tells whether the other comparator's sort direction is reversed.
*/
public boolean isReversed()
{
return reversed;
}
/**
Determines whether the other comparator's sort direction is reversed.
*/
public void setReversed(boolean reversed)
{
this.reversed = reversed;
}
/**
Toggles the current "sort direction".
*/
public void toggleReversed()
{
reversed = !reversed;
}
/**
The other comparator.
*/
private final Comparator comparator;
/**
Whether the other comparator's sort direction is reversed.
*/
private boolean reversed;
}
public String refineFilterString (String filterString)
{
if ( ( null == filterString ) || ( 0 >= filterString.length() ) )
{
filterString = ".*"; //show All
}
if ( ! filterString.equalsIgnoreCase(".*") )
{
if(filterString.indexOf('*')>=0)
{
filterString = filterString.replaceAll("",".");
}
else
{
filterString = "." + filterString + ".";
}
if(!filterString.endsWith("") && !filterString.startsWith(".") && (filterString.indexOf('*')> 0))
{
filterString = "." + filterString + ".";
}
}
return filterString;
}
}
Hi Shah,
Copy service will work for same structure. create the same structure ,not only the last node & use WDCopyService.copySubtree();
regards
Sumit
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.
Hello Sumit,
thanks for your reply,
I used following code:
WDCopyService.copySubtree(wdContext.nodeRFC_ShippingPartner_In().nodeOutput().nodeZmat_Fg(), wdContext.nodeRFC_ShippingPartner_In_().nodeOutput_().nodeZmat_Fg_());
( I used this code in the wdModifyview of my popup view )
but get the following exception.
The initial exception that caused the request to fail, was:
com.sap.tc.webdynpro.progmodel.context.ContextException: Node(PopupView.RFC_ShippingPartner_In_.Output_.Zmat_Fg_): cannot bind or add elements because the node has no valid parent
How I can manully copy the modle context to other model context ?
Regards,
Edited by: Shah H on Dec 19, 2007 11:15 AM
Hello Sumit,
now filtring is not working and secondly in popup it shows me all values, but when I click one row then always the first row is copied to the parent view ( as I menioned I have dialog ( carries a table ) and this dialoug is a view.
My filtring is only working when both modle nodes are binded to controller ( but in that case once value is filtred I cant retrieve the all RESULT again once I clear the filtered value )...
Now I am thinking to execute the RFC again when filter value is space or so ? what do you think ?
Regards,
Edited by: Shah H on Dec 19, 2007 2:02 PM
User | Count |
---|---|
80 | |
24 | |
11 | |
9 | |
7 | |
6 | |
5 | |
5 | |
4 | |
4 |
You must be a registered user to add a comment. If you've already registered, sign in. Otherwise, register and sign in.