Martin Sladecek martin.sladecek at
Tue Jan 8 00:55:07 PST 2013

Hi Jonathan,

the problem I see is not that you would modify the Comparator, but the 
fact that you expect the "items" list to have SortedList in the chain. 
What would you do otherwise, modify the list in place as you do now?
This would mean the developer has to be really careful when setting the 
items of a TableView to get the desired behaviour.

Let's say we want to have column sorting, but don't want to modify items 
in place, so we'd something like

TransformationList items = list.sorted(comparator);
// Do something with items

Now there are couple of issues here.
First, what comparator to provide to the list if I have no preferred 
order? Using no comparator will result in attempt to use natural 
ordering, but the items in the lists doesn't have be Comparable.
Second, we need a special interface for SortedList so that the TableView 
can change the comparator. I agree that the column ordering takes 
precedence over the default order, but what if something like this 
happens after a column is clicked?


The table view would still show it's sorted by columns, but it would 
actually be sorted by some different comparator. You'd also have to be 
careful not to rely on your Comparator being the current Comparator.

I think you can avoid both by doing the column sort internally, and 
provide the TransformationList for the developer as a view. So, the same 
as above can be achieved this way:

TransformationList items = tableView.getViewList();
// Do something with items

You don't have to care about Comparator (it's internally managed by the 
TableView). As we have no special interface for SortedList, there's no 
way how to change the Comparator through the TransformationList 
interface. Only table can do that, in case it used 
sorted(ObservableValue<Comparator>) method.
If somebody wants some different order, sorted() can be used explicitly:

TransformationList items = tableView.getItemsList();

Column order (if defined & used) always takes precedence over the 
basicOrderComapartor (as we basically have two sorted lists), and the 
user-defined order is used when column ordering is turned off.

No need to special case anything in TableView, no differences in 
behaviour for different items types (plain ObservableList vs. 
SortedList), no changes to the provided list.


On 01/08/2013 09:06 AM, Jonathan Giles wrote:
> I'm probably just being really dense, but I can't see the problem; 
> TableView doesn't do anything special when it comes to sorting by 
> columns. All I do behind the scenes is create a Comparator and use 
> that to sort the list whenever a user/developer modifies the relevant 
> sorting properties on TableView and / or TableColumn. When a sort 
> needs to be executed, I create a Comparator that first sorts using the 
> Comparator from the first TableColumn in the TableView.sortOrder list, 
> and where there are two cells that are equal I sort using the 
> Comparator from the second column (if one is specified), and so on 
> (using third, fourth, and additional columns, as specified in the 
> TableView.sortOrder list).
> At present the TableView simply runs this sort on the items list, 
> modifying it in place (yuck). However, with the forthcoming 
> availability of a sorted list API, can't I continue to do this, but 
> without the need to modify the source list (that is, by creating an 
> internal sorted list when a sort occurs), and with the benefit that I 
> could trivially return to the original unsorted state by getting the 
> source list out of the sorted list?
> Perhaps you're saying that I need to special case this so that I don't 
> change the Comparator set on the sortedList? That is an important 
> point to consider: what takes precedence - the Comparator specified by 
> the developer against the sorted list, or the one specified by the 
> user when they click on columns? But I'm also thinking that I'm simply 
> not understanding an important consideration of your sorting / 
> filtering APIs, so it would be great to clarify what that is, if that 
> is the case!
> -- Jonathan
> On 8/01/2013 8:45 p.m., Martin Sladecek wrote:
>> Unfortunately, not all cases can be solved naturally by wrapping the 
>> list in sorted/filtered wrapper.
>> One exception to that is sorting by columns. It's something TableView 
>> does internally and it requires some model/view mapping.
>> While I understand the benefits of having view-model data, I really 
>> don't know how to solve this case without the mapping provided by the 
>> TableView. If the user would use some filtered/sorted wrapper, his 
>> API has to deal with index conversions anyway, using the 
>> TransformationList API (the top wrapper being the view, while the 
>> original list is in fact the model). E.g. you need this if you want 
>> to add something after some item in the table.
>> So can't we just say "Hey, use the TransformationList provided by 
>> TableView.getViewList() for your model-view conversions instead of 
>> the list you passed into setItems()".
>> All the indexes in the list will be relative to the getViewList() 
>> instead of the items and that's it. The TableView doesn't have to 
>> treat different items differently or rely on some weird conditions 
>> like having a SortedList in the chain (which it does now if you look 
>> at TableView.sort()). So, every kind of ObservableList would just 
>> work (mutable, immutable, transformation, ...) without some special 
>> treatment from the TableView.
>> -Martin

More information about the openjfx-dev mailing list