Eclipse Community Forums
Forum Search:

Search      Help    Register    Login    Home
Home » Eclipse Projects » Nebula » Reactions to CompositeTable API
Reactions to CompositeTable API [message #18076] Thu, 30 November 2006 15:44 Go to next message
Matthew Hall is currently offline Matthew HallFriend
Messages: 368
Registered: July 2009
Senior Member
I've been looking over the API for CompositeTable and wanted to share
some of my reactions for discussion.

First of all, this control is a great idea and as evidenced by the
response on the newsgroups, is useful for a fair number of people,
including myself. However the stated goal of Nebula is to be a proving
ground for custom widgets, with the eventual goal of those widgets being
adopted into SWT proper. I think that the CompositeTable API deviates
from SWT conventions to such a degree that will make its adoption into
SWT unlikely. Thus I would like to see CompositeTable refactored to
makes its API more like the rest of SWT.

For example: Table, Tree and TabFolder expose their content through
TableItem, TreeItem and TabItem and developers are used to interacting
with them. By contrast, CompositeTable uses prototyping to define rows
and possibly headers. This is a very unfamiliar approach in Java, let
alone in SWT. I think everyone would be more comfortable with a
CompositeItem concept rather than this nebulous (forgive the pun)
prototyping scheme.

On the same note, the Table and Tree widgets have a method setItemCount
to set the number of items, whereas in CompositeTable this is called
setNumRowsInCollection.

I don't like the design-mode / active-mode paradigm.

Then there is the use of reflection. Although I recognize that Dave
Orme (who authored the control) would be quite comfortable with
reflection, given his role in VE and data binding, I am nonetheless
uncomfortable with it. Using reflection is a performance hit, is
brittle, and really isn't necessary if we just invent an interface to
replace it (ICompositeRowBuilder). Moreover it makes adoption into SWT
impossible since (as I understand it) reflection is not available in the
CDC-1.0/Foundation-1.0 runtime environment.

And I REALLY don't like being forced to extend composite for my rows,
when we could just define an interface that creates and manages a
composite instead. This is a very Swing way of using SWT.

It would also seem more appropriate to use SWT.SetData listeners like
the other virtual controls instead of addRowContentProvider.

Just my $0.02. What does everybody else think?

(Should this be posted in Bugzilla instead?)

Thanks for listening

Matthew Hall
Re: Reactions to CompositeTable API [message #18758 is a reply to message #18076] Thu, 30 November 2006 18:13 Go to previous messageGo to next message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
Matthew Hall wrote:
> I've been looking over the API for CompositeTable and wanted to share
> some of my reactions for discussion.

Thanks for your thoughtful comments!

> First of all, this control is a great idea and as evidenced by the
> response on the newsgroups, is useful for a fair number of people,
> including myself.

Thanks!

> However the stated goal of Nebula is to be a proving
> ground for custom widgets, with the eventual goal of those widgets being
> adopted into SWT proper. I think that the CompositeTable API deviates
> from SWT conventions to such a degree that will make its adoption into
> SWT unlikely. Thus I would like to see CompositeTable refactored to
> makes its API more like the rest of SWT.

To the extent that this is possible, I'd like to see this too.

> For example: Table, Tree and TabFolder expose their content through
> TableItem, TreeItem and TabItem and developers are used to interacting
> with them. By contrast, CompositeTable uses prototyping to define rows
> and possibly headers. This is a very unfamiliar approach in Java, let
> alone in SWT. I think everyone would be more comfortable with a
> CompositeItem concept rather than this nebulous (forgive the pun)
> prototyping scheme.

Can you explain what you mean by a CompositeItem object? I'm a bit
confused.

The reason I'm confused is that CompositeTable really has *no* concept
that is similar to the *Item concept in the standard controls.

For example:

1) The *Item concept in SWT mainly represents what *data* will be placed
in the specified columns, along with some layout information (width, etc).

2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
items for *all* rows that have been displayed and then never destroys them.

In contrast, the row objects in CompositeTable correspond to exactly the
SWT controls that are visible. Once a row becomes invisible, it ceases
to exist as far as CompositeTable's layout is concerned. If topRow() is
0, the visible table height is 20 rows, and numRowsInCollection is 25,
CompositeTable still only maintains row objects for the top 20 rows.
Not only that, but as soon as the user scrolls forward one row, the top
row control is immediately discarded, a new one is created representing
row 21, and all the controls in the middle are shifted up. (In
practice, CompositeTable recycles the row objects, so there is no
performance loss from creating and disposing controls.)

I could rename the "row" concept to "Item", but I'm concerned that this
would be confusing. They just are really different things, and behave
completely differently.

Did I correctly understand your suggestion?

> On the same note, the Table and Tree widgets have a method setItemCount
> to set the number of items, whereas in CompositeTable this is called
> setNumRowsInCollection.

If I called it setItemCount, this would imply that if you
setItemCount(1000000), that there would be a million CompositeTableItem
objects somewhere, which simply isn't true.

> I don't like the design-mode / active-mode paradigm.

Neither do I.

There are two reasons this exists: One major goal I had when creating
CompositeTable is that it would be simple to use within Visual Editor.

I could use Beans.isDesignTime() in the control and maybe I should do
that, but I wanted the control behave inside VE exactly the way it
behaves at run-time. This way you can more easily learn to use the
control by changing the properties interactively in VE and watching what
happens.

The only way to accomplish this is to have a property that explicitly
switches the control from design-time behavior to run-time behavior.

The second reason is that JavaBeans isn't in Foundation profile. So in
order to support Foundation, I can't use Beans.isDesignTime().

But maybe this property was a bad idea.

I'd be happy for feedback on this. What do folks think?

> Then there is the use of reflection. Although I recognize that Dave
> Orme (who authored the control) would be quite comfortable with
> reflection, given his role in VE and data binding, I am nonetheless
> uncomfortable with it. Using reflection is a performance hit, is
> brittle, and really isn't necessary if we just invent an interface to
> replace it (ICompositeRowBuilder). Moreover it makes adoption into SWT
> impossible since (as I understand it) reflection is not available in the
> CDC-1.0/Foundation-1.0 runtime environment.

There is a really good question here, but a few misconceptions too.
I'll clear away the misconceptions first, and then we can hopefully
tackle the underlying question more productively:

1) On Foundation support: reflection is there but not dynamic proxies or
JavaBean support.

2) Regarding performance, reflection is only used to construct new row
controls. But once a row control is constructed, it is never destroyed
until the entire CompositeTable control is destroyed. (Instead,
CompositeTable recycles row objects.) So if your table has 20 rows of
data in it, there will be exactly 20 reflection calls the first time
your data is displayed and no more reflection calls after that. Since
reflection is never used any more after the row controls are
constructed, performance just isn't an issue here.

(CompositeTable never creates more row objects than can be displayed in
the window at once, so the upper bound of row controls created is
exactly the same number as the number of controls you would have if you
created the same layout by hand.)

3) I don't understand how reflection is brittle in this case?

Now on to the underlying question (the whole reason I use reflection to
begin with):

> And I REALLY don't like being forced to extend composite for my rows,
> when we could just define an interface that creates and manages a
> composite instead. This is a very Swing way of using SWT.

As stated above, a design goal for CompositeTable was to be able to edit
the table visually using Visual Editor. Visual Editor knows how to edit
a custom Composite, but not how to edit a JFace-like createControl() UI
factory.

However, I would like to be able to accommodate folks that would prefer
to use an interface. If someone can propose an API that makes sense and
doesn't lose the VE support, I'd be very glad to listen.

> It would also seem more appropriate to use SWT.SetData listeners like
> the other virtual controls instead of addRowContentProvider.

Again, it's a possibility to try to mimic the SWT names, but don't you
feel that folks will be confused here? In CompositeTable's event, one
normally doesn't set data into some *Item object, but rather sets data
into real SWT controls in your row object or possibly uses data binding
to bind those controls to a domain model object.

What CompositeTable does here seems closer conceptually to the JFace
content provider concept, which is why this name was chosen.

I'm willing to rename this, but I'm concerned about confusion.

> Just my $0.02. What does everybody else think?

Thanks for your feedback!

In balance, CompositeTable tries to reflect and synthesize ideas from
all of SWT + JFace + Visual Editor + Eclipse Data binding APIs. My hope
is that this will make folks more productive and result in more
maintainable applications.

Thanks for trying to help make it better.

> (Should this be posted in Bugzilla instead?)
>
> Thanks for listening

I think that the newsgroup is the best place for this discussion right
now. If specific feature requests come out of this discussion, those
should go into Bugzilla.

Thanks for writing. :)


Best regards,

Dave Orme
Re: Reactions to CompositeTable API [message #18825 is a reply to message #18758] Thu, 30 November 2006 22:34 Go to previous messageGo to next message
Matthew Hall is currently offline Matthew HallFriend
Messages: 368
Registered: July 2009
Senior Member
A snippet's worth a thousand words:


CompositeTable table = new CompositeTable(parent, SWT.VIRTUAL | SWT.BORDER);

// I like the class as a manager for the row, I just don't think it
// should extend Composite by design
// Adding this interface will remove all that reflection code
interface ICompositeRow {
   // Implementers are responsible for making getControl() return the
   // created control
   void createControl(CompositeTable table);
   Control getControl();
}

abstract class CompositeRow implements ICompositeRow {
   Control control;

   Control getControl() {
     return control;
   }

   /** Sets the control returned by getControl */
   void setControl(Control control) {
     this.control = control;
   }
}

class MyHeader extends CompositeRow {
   Label first;
   Label last;

   void createControl(CompositeTable table) {
     Composite composite = new Composite(table, SWT.NONE);
     first = new Label(composite, SWT.NONE);
     last = new Label(composite, SWT.NONE);
     first.setText("First");
     last.setText("Last");
     setControl(composite);
   }
}

table.setHeaderProvider(new IRowProvider() {
   ICompositeRow createRow() { return new MyHeader(); }
});

class MyRow implements ICompositeRow {
   Text first;
   Text last;

   void createControl(CompositeTable table) {
     Composite composite = new Composite(table, SWT.NONE);
     first = new Text(composite, SWT.BORDER);
     last = new Text(composite, SWT.BORDER);
     setControl(composite);
   }
}

table.setRowProvider(new IRowProvider() {
   ICompositeRow createRow() { return new MyRow(); }
});

// The CompositeItem is basically the JFace wrapper around the content
abstract class CompositeItem extends Item {
   CompositeItem(CompositeTable table, int style) {
     super(table, style);
     table.addItem(this);
   }

   CompositeItem(CompositeTable table, int style, int index) {
     super(table, style);
     table.addItem(this, index);
   }

   // This property is managed by CompositeTable as it scrolls up
   // and down
   ICompositeRow row = null;
   ICompositeRow getRow() { return row; }
   void setRow(ICompositeRow row) {
     if (this.row != null)
       unhookListeners(this.row);

     this.row = row;
     updateRow();

     if (row != null)
       hookListeners(row);
   }

   // These methods may be over-designed, but just a thought
   // off the top of my head
   // DataBinding would really help here
   abstract void hookListeners(ICompositeRow row);
   abstract void unhookListeners(ICompositeRow row);
   abstract void updateRow();
}

class MyItem extends CompositeItem implements Listener {
   Name name = null;

   MyItem(CompositeTable table, int style) {
     super(table, style);
   }

   MyItem(CompositeTable table, int style, int index, Name name) {
     super(table, style, index);
   }

   Name getName() { return name; }
   void setName(Name name) {
     this.name = name;
     updateRow();
   }

   void hookListeners(ICompositeRow row) {
     MyRow r = (MyRow) row;
     r.first.addListener(SWT.Modify, this);
     r.last.addListener(SWT.Modify, this);
   }

   void unhookListeners(ICompositeRow row) {
     MyRow r = (MyRow) row;
     r.first.removeListener(SWT.Modify, this);
     r.last.removeListener(SWT.Modify, this);
   }

   void updateRow() {
     MyRow r = (MyRow) getRow();
     if (r == null) return;
     r.first.setText(name == null ? "" : name.getFirst());
     r.last.setText(name == null ? "" : name.getLast());
   }

   void handleEvent(Event e) {
     if (name == null) return;

     MyRow row = (MyRow) getRow();
     if (e.widget == row.first)
       name.setFirst(row.first.getText());
     else if (e.widget == row.last)
       name.setLast(row.last.getText());
   }
}

table.setItemProvider(new ICompositeItemProvider() {
   CompositeItem createItem(CompositeTable table, int style, int index) {
     return new MyItem(table, style, index);
   }
});

table.addListener(SWT.SetData, new Listener() {
   void handleEvent(Event e) {
     MyItem item = (MyItem) e.item;
     int index = table.indexOf(item);
     item.setName(Names.get(index));
   }
});

table.setItemCount(Names.getCount());



This is just a rough sketch of what I had in mind.

> 1) The *Item concept in SWT mainly represents what *data* will be placed
> in the specified columns, along with some layout information (width, etc).
>
> 2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
> items for *all* rows that have been displayed and then never destroys them.

As outlined above, an Item is a separate concept from a Row. The item
maps to the data, where the Row maps to the visible display.

> If I called it setItemCount, this would imply that if you
> setItemCount(1000000), that there would be a million CompositeTableItem
> objects somewhere, which simply isn't true.

Not necessarily. This behavior could be emulated and items created on
the fly as they are needed for display by the ICompositeItemProvider,
and initialized by the SWT.SetData listener.

It would also be useful to have SWT.VIRTUAL be an option instead of a
given. This would allow users to just instantiate their items as needed
for small collections, which would result in simpler code:

for (int i = 0; i < Names.getCount(); i++)
   new MyItem(table, SWT.NONE).setName(Names.get(i));


>> I don't like the design-mode / active-mode paradigm.
>
> Neither do I.
>
> There are two reasons this exists: One major goal I had when creating
> CompositeTable is that it would be simple to use within Visual Editor.
>
> I could use Beans.isDesignTime() in the control and maybe I should do
> that, but I wanted the control behave inside VE exactly the way it
> behaves at run-time. This way you can more easily learn to use the
> control by changing the properties interactively in VE and watching what
> happens.
>
> The only way to accomplish this is to have a property that explicitly
> switches the control from design-time behavior to run-time behavior.
>
> The second reason is that JavaBeans isn't in Foundation profile. So in
> order to support Foundation, I can't use Beans.isDesignTime().
>
> But maybe this property was a bad idea.
>
> I'd be happy for feedback on this. What do folks think?
>

Perhaps make the property false by default? The design changes I'm
suggesting would not prevent this option, but it is a little jarring to
have this setDesignTime(false) method call in the middle of my code.

>> Then there is the use of reflection. Although I recognize that Dave
>> Orme (who authored the control) would be quite comfortable with
>> reflection, given his role in VE and data binding, I am nonetheless
>> uncomfortable with it. Using reflection is a performance hit, is
>> brittle, and really isn't necessary if we just invent an interface to
>> replace it (ICompositeRowBuilder). Moreover it makes adoption into
>> SWT impossible since (as I understand it) reflection is not available
>> in the CDC-1.0/Foundation-1.0 runtime environment.
>
> There is a really good question here, but a few misconceptions too. I'll
> clear away the misconceptions first, and then we can hopefully tackle
> the underlying question more productively:
>
> 1) On Foundation support: reflection is there but not dynamic proxies or
> JavaBean support.

Good to know

>
> 2) Regarding performance, reflection is only used to construct new row
> controls. But once a row control is constructed, it is never destroyed
> until the entire CompositeTable control is destroyed. (Instead,
> CompositeTable recycles row objects.) So if your table has 20 rows of
> data in it, there will be exactly 20 reflection calls the first time
> your data is displayed and no more reflection calls after that. Since
> reflection is never used any more after the row controls are
> constructed, performance just isn't an issue here.

True, but a regular old java interface like IRowProvider is much more
comfortable to Java programmers than duck typing.

> 3) I don't understand how reflection is brittle in this case?

It excludes the possibility of other constructor signatures, such as
MyCompositeRow(CompositeTable table) where the style bit is implicit.
Although considered bad form in SWT, this is a legitimate choice for the
developer.

> Now on to the underlying question (the whole reason I use reflection to
> begin with):
>
>> And I REALLY don't like being forced to extend composite for my rows,
>> when we could just define an interface that creates and manages a
>> composite instead. This is a very Swing way of using SWT.
>
> As stated above, a design goal for CompositeTable was to be able to edit
> the table visually using Visual Editor. Visual Editor knows how to edit
> a custom Composite, but not how to edit a JFace-like createControl() UI
> factory.

The JFace createControl() factory paradigm is pervasive throughout the
platform. I think the "knows how to edit" use case really belongs in
VE, not in each control we hope to use in VE.

> However, I would like to be able to accommodate folks that would prefer
> to use an interface. If someone can propose an API that makes sense and
> doesn't lose the VE support, I'd be very glad to listen.

Perhaps you could point me to some HOWTO's or tutorials for teaching VE
how to design custom controls, and I'll help you work on it.

>> It would also seem more appropriate to use SWT.SetData listeners like
>> the other virtual controls instead of addRowContentProvider.
>
> Again, it's a possibility to try to mimic the SWT names, but don't you
> feel that folks will be confused here?

That's a question for the bystanders!

Maybe it would help if we following Steve Northover's advice and set the
SWT.SMART bit on the CompositeTable. :)

> In CompositeTable's event, one
> normally doesn't set data into some *Item object, but rather sets data
> into real SWT controls in your row object or possibly uses data binding
> to bind those controls to a domain model object.

Sorry, I should have explained that in my original post. In my proposed
design the concrete CompositeItem subclass is responsible for populating
the ICompositeRow fields and managing the binding between those
controls. This is a departure from SWT conventions, but as you say this
is a different beast, and I felt it was the least "weird" of approaches.
Your mileage my vary.

> What CompositeTable does here seems closer conceptually to the JFace
> content provider concept, which is why this name was chosen.
>
> I'm willing to rename this, but I'm concerned about confusion.

To me this design feels a lot clearer and simpler, but I acknowledge
that this may be confusing to others.

> In balance, CompositeTable tries to reflect and synthesize ideas from
> all of SWT + JFace + Visual Editor + Eclipse Data binding APIs. My hope
> is that this will make folks more productive and result in more
> maintainable applications.

Thanks Dave for taking the time to respond.

Matthew
Re: Reactions to CompositeTable API [message #18916 is a reply to message #18825] Fri, 01 December 2006 14:34 Go to previous messageGo to next message
Chris Gross is currently offline Chris GrossFriend
Messages: 253
Registered: July 2009
Senior Member
Hi Matthew,

Can I ask a (perhaps dumb) question? You seem to want to change alot of
the CompositeTable API and make it fit in better with SWT, etc. With
all these changes wouldn't the end result be much like a regular SWT
Table that is populated with widgets using TableEditors (except that the
editors are only created on visible rows)? In other words, it sounds
like alot of what you don't like is what makes CompositeTable unique.
What is the feature (or features) from CompositeTable that you think are
the killer (i.e. killer in a good way ;)?

Regards,
-Chris

Matthew Hall wrote:
> A snippet's worth a thousand words:
>
>
> 
> CompositeTable table = new CompositeTable(parent, SWT.VIRTUAL | 
> SWT.BORDER);
> 
> // I like the class as a manager for the row, I just don't think it
> // should extend Composite by design
> // Adding this interface will remove all that reflection code
> interface ICompositeRow {
>   // Implementers are responsible for making getControl() return the
>   // created control
>   void createControl(CompositeTable table);
>   Control getControl();
> }
> 
> abstract class CompositeRow implements ICompositeRow {
>   Control control;
> 
>   Control getControl() {
>     return control;
>   }
> 
>   /** Sets the control returned by getControl */
>   void setControl(Control control) {
>     this.control = control;
>   }
> }
> 
> class MyHeader extends CompositeRow {
>   Label first;
>   Label last;
> 
>   void createControl(CompositeTable table) {
>     Composite composite = new Composite(table, SWT.NONE);
>     first = new Label(composite, SWT.NONE);
>     last = new Label(composite, SWT.NONE);
>     first.setText("First");
>     last.setText("Last");
>     setControl(composite);
>   }
> }
> 
> table.setHeaderProvider(new IRowProvider() {
>   ICompositeRow createRow() { return new MyHeader(); }
> });
> 
> class MyRow implements ICompositeRow {
>   Text first;
>   Text last;
> 
>   void createControl(CompositeTable table) {
>     Composite composite = new Composite(table, SWT.NONE);
>     first = new Text(composite, SWT.BORDER);
>     last = new Text(composite, SWT.BORDER);
>     setControl(composite);
>   }
> }
> 
> table.setRowProvider(new IRowProvider() {
>   ICompositeRow createRow() { return new MyRow(); }
> });
> 
> // The CompositeItem is basically the JFace wrapper around the content
> abstract class CompositeItem extends Item {
>   CompositeItem(CompositeTable table, int style) {
>     super(table, style);
>     table.addItem(this);
>   }
> 
>   CompositeItem(CompositeTable table, int style, int index) {
>     super(table, style);
>     table.addItem(this, index);
>   }
> 
>   // This property is managed by CompositeTable as it scrolls up
>   // and down
>   ICompositeRow row = null;
>   ICompositeRow getRow() { return row; }
>   void setRow(ICompositeRow row) {
>     if (this.row != null)
>       unhookListeners(this.row);
> 
>     this.row = row;
>     updateRow();
> 
>     if (row != null)
>       hookListeners(row);
>   }
> 
>   // These methods may be over-designed, but just a thought
>   // off the top of my head
>   // DataBinding would really help here
>   abstract void hookListeners(ICompositeRow row);
>   abstract void unhookListeners(ICompositeRow row);
>   abstract void updateRow();
> }
> 
> class MyItem extends CompositeItem implements Listener {
>   Name name = null;
> 
>   MyItem(CompositeTable table, int style) {
>     super(table, style);
>   }
> 
>   MyItem(CompositeTable table, int style, int index, Name name) {
>     super(table, style, index);
>   }
> 
>   Name getName() { return name; }
>   void setName(Name name) {
>     this.name = name;
>     updateRow();
>   }
> 
>   void hookListeners(ICompositeRow row) {
>     MyRow r = (MyRow) row;
>     r.first.addListener(SWT.Modify, this);
>     r.last.addListener(SWT.Modify, this);
>   }
> 
>   void unhookListeners(ICompositeRow row) {
>     MyRow r = (MyRow) row;
>     r.first.removeListener(SWT.Modify, this);
>     r.last.removeListener(SWT.Modify, this);
>   }
> 
>   void updateRow() {
>     MyRow r = (MyRow) getRow();
>     if (r == null) return;
>     r.first.setText(name == null ? "" : name.getFirst());
>     r.last.setText(name == null ? "" : name.getLast());
>   }
> 
>   void handleEvent(Event e) {
>     if (name == null) return;
> 
>     MyRow row = (MyRow) getRow();
>     if (e.widget == row.first)
>       name.setFirst(row.first.getText());
>     else if (e.widget == row.last)
>       name.setLast(row.last.getText());
>   }
> }
> 
> table.setItemProvider(new ICompositeItemProvider() {
>   CompositeItem createItem(CompositeTable table, int style, int index) {
>     return new MyItem(table, style, index);
>   }
> });
> 
> table.addListener(SWT.SetData, new Listener() {
>   void handleEvent(Event e) {
>     MyItem item = (MyItem) e.item;
>     int index = table.indexOf(item);
>     item.setName(Names.get(index));
>   }
> });
> 
> table.setItemCount(Names.getCount());
> 
> 

>
> This is just a rough sketch of what I had in mind.
>
>> 1) The *Item concept in SWT mainly represents what *data* will be
>> placed in the specified columns, along with some layout information
>> (width, etc).
>>
>> 2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
>> items for *all* rows that have been displayed and then never destroys
>> them.
>
> As outlined above, an Item is a separate concept from a Row. The item
> maps to the data, where the Row maps to the visible display.
>
>> If I called it setItemCount, this would imply that if you
>> setItemCount(1000000), that there would be a million
>> CompositeTableItem objects somewhere, which simply isn't true.
>
> Not necessarily. This behavior could be emulated and items created on
> the fly as they are needed for display by the ICompositeItemProvider,
> and initialized by the SWT.SetData listener.
>
> It would also be useful to have SWT.VIRTUAL be an option instead of a
> given. This would allow users to just instantiate their items as needed
> for small collections, which would result in simpler code:
>
>
> for (int i = 0; i < Names.getCount(); i++)
>   new MyItem(table, SWT.NONE).setName(Names.get(i));
> 

>
>>> I don't like the design-mode / active-mode paradigm.
>>
>> Neither do I.
>>
>> There are two reasons this exists: One major goal I had when creating
>> CompositeTable is that it would be simple to use within Visual Editor.
>>
>> I could use Beans.isDesignTime() in the control and maybe I should do
>> that, but I wanted the control behave inside VE exactly the way it
>> behaves at run-time. This way you can more easily learn to use the
>> control by changing the properties interactively in VE and watching
>> what happens.
>>
>> The only way to accomplish this is to have a property that explicitly
>> switches the control from design-time behavior to run-time behavior.
>>
>> The second reason is that JavaBeans isn't in Foundation profile. So
>> in order to support Foundation, I can't use Beans.isDesignTime().
>>
>> But maybe this property was a bad idea.
>>
>> I'd be happy for feedback on this. What do folks think?
>>
>
> Perhaps make the property false by default? The design changes I'm
> suggesting would not prevent this option, but it is a little jarring to
> have this setDesignTime(false) method call in the middle of my code.
>
>>> Then there is the use of reflection. Although I recognize that Dave
>>> Orme (who authored the control) would be quite comfortable with
>>> reflection, given his role in VE and data binding, I am nonetheless
>>> uncomfortable with it. Using reflection is a performance hit, is
>>> brittle, and really isn't necessary if we just invent an interface to
>>> replace it (ICompositeRowBuilder). Moreover it makes adoption into
>>> SWT impossible since (as I understand it) reflection is not available
>>> in the CDC-1.0/Foundation-1.0 runtime environment.
>>
>> There is a really good question here, but a few misconceptions too.
>> I'll clear away the misconceptions first, and then we can hopefully
>> tackle the underlying question more productively:
>>
>> 1) On Foundation support: reflection is there but not dynamic proxies
>> or JavaBean support.
>
> Good to know
>
>>
>> 2) Regarding performance, reflection is only used to construct new row
>> controls. But once a row control is constructed, it is never
>> destroyed until the entire CompositeTable control is destroyed.
>> (Instead, CompositeTable recycles row objects.) So if your table has
>> 20 rows of data in it, there will be exactly 20 reflection calls the
>> first time your data is displayed and no more reflection calls after
>> that. Since reflection is never used any more after the row controls
>> are constructed, performance just isn't an issue here.
>
> True, but a regular old java interface like IRowProvider is much more
> comfortable to Java programmers than duck typing.
>
>> 3) I don't understand how reflection is brittle in this case?
>
> It excludes the possibility of other constructor signatures, such as
> MyCompositeRow(CompositeTable table) where the style bit is implicit.
> Although considered bad form in SWT, this is a legitimate choice for the
> developer.
>
>> Now on to the underlying question (the whole reason I use reflection
>> to begin with):
>>
>>> And I REALLY don't like being forced to extend composite for my rows,
>>> when we could just define an interface that creates and manages a
>>> composite instead. This is a very Swing way of using SWT.
>>
>> As stated above, a design goal for CompositeTable was to be able to
>> edit the table visually using Visual Editor. Visual Editor knows how
>> to edit a custom Composite, but not how to edit a JFace-like
>> createControl() UI factory.
>
> The JFace createControl() factory paradigm is pervasive throughout the
> platform. I think the "knows how to edit" use case really belongs in
> VE, not in each control we hope to use in VE.
>
>> However, I would like to be able to accommodate folks that would
>> prefer to use an interface. If someone can propose an API that makes
>> sense and doesn't lose the VE support, I'd be very glad to listen.
>
> Perhaps you could point me to some HOWTO's or tutorials for teaching VE
> how to design custom controls, and I'll help you work on it.
>
>>> It would also seem more appropriate to use SWT.SetData listeners like
>>> the other virtual controls instead of addRowContentProvider.
>>
>> Again, it's a possibility to try to mimic the SWT names, but don't you
>> feel that folks will be confused here?
>
> That's a question for the bystanders!
>
> Maybe it would help if we following Steve Northover's advice and set the
> SWT.SMART bit on the CompositeTable. :)
>
>> In CompositeTable's event, one normally doesn't set data into some
>> *Item object, but rather sets data into real SWT controls in your row
>> object or possibly uses data binding to bind those controls to a
>> domain model object.
>
> Sorry, I should have explained that in my original post. In my proposed
> design the concrete CompositeItem subclass is responsible for populating
> the ICompositeRow fields and managing the binding between those
> controls. This is a departure from SWT conventions, but as you say this
> is a different beast, and I felt it was the least "weird" of approaches.
> Your mileage my vary.
>
>> What CompositeTable does here seems closer conceptually to the JFace
>> content provider concept, which is why this name was chosen.
>>
>> I'm willing to rename this, but I'm concerned about confusion.
>
> To me this design feels a lot clearer and simpler, but I acknowledge
> that this may be confusing to others.
>
>> In balance, CompositeTable tries to reflect and synthesize ideas from
>> all of SWT + JFace + Visual Editor + Eclipse Data binding APIs. My
>> hope is that this will make folks more productive and result in more
>> maintainable applications.
>
> Thanks Dave for taking the time to respond.
>
> Matthew
Re: Reactions to CompositeTable API [message #18982 is a reply to message #18916] Fri, 01 December 2006 17:22 Go to previous messageGo to next message
Matthew Hall is currently offline Matthew HallFriend
Messages: 368
Registered: July 2009
Senior Member
Chris Gross wrote:
> Can I ask a (perhaps dumb) question? You seem to want to change a lot of
> the CompositeTable API and make it fit in better with SWT, etc.

I'm not trying to rock the boat here. David Orme himself said that he
want to avoid confusing users. I'm making these suggestions because I
think it will make the control simpler and more intuitive. And I'm not
suggesting that my ideas are the best--I'm trying to get a dialog going.

> With all these changes wouldn't the end result be much like a regular SWT
> Table that is populated with widgets using TableEditors (except that the
> editors are only created on visible rows)? In other words, it sounds
> like alot of what you don't like is what makes CompositeTable unique.

Not really. I'm suggesting changes to the API to make what
CompositeTable does more accessible to SWT programmers. The
reservations I have are:

* I dislike reflection because however you use reflection becomes de
facto API, except the compiler can't check for bad usage. Who knows if
somebody will refactor your Row class down the road, not knowing it
*has* to have a (Composite, int) constructor? The compiler will *never*
catch this. A documented interface instead of reflection will avoid
this problem. Besides, it may be possible to just have the default
IRowProvider perform this exact behavior so that current CompositeTable
users can just keep doing prototyping if they prefer.
* SWT programmers are used to working with *Items. Working with items
the non-virtual way is much easier than the virtual way, and I would
like an option between the two.
* Renaming some of the API (numRowsInCollection == itemCount) to match
SWT naming conventions will make using this control more intuitive.

> What is the feature (or features) from CompositeTable that you think are
> the killer (i.e. killer in a good way ;)?

* The ability to use controls at all times, instead of having to click
the cell to bring up the editor.
* The ability to lay out those controls any way you like within the row
if the standard left-to-right columnar layout doesn't suit you.

I'm willing to program these changes myself and submit a patch. I just
wanted to see what the general consensus is before I started.

Matt
Re: Reactions to CompositeTable API [message #19004 is a reply to message #18825] Fri, 01 December 2006 17:37 Go to previous messageGo to next message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
Matthew Hall wrote:
> A snippet's worth a thousand words:

Agreed. How's this?

/**
* A CompositeTable editing first/last name pairs
*
* @author djo
*/
public class CompositeTableSnippet2 {
// First some data to edit...
private static class Name {
public String first;
public String last;
public Name(String first, String last) {
this.first = first;
this.last = last;
}
}

static Name[] swtCommitters = new Name[] {
new Name("Grant", "Gayed"),
new Name("Veronika", "Irvine"),
new Name("Steve", "Northover"),
new Name("Mike", "Wilson"),
new Name("Christophe", "Cornu"),
new Name("Lynne", "Kues"),
new Name("Silenio", "Quarti"),
new Name("Tod", "Creasey"),
new Name("Felipe", "Heidrich"),
new Name("Billy", "Biggs"),
new Name("B", "Shingar")
};

// Now, define the table's header and row objects
//
// A tabular layout is desired, so no layout manager is needed
// on the header
// or row. CompositeTable will handle the layout automatically.
// However,
// if you supply a layout manager, CompositeTable will respect
// and use it.

private static class Header extends Composite {
public Header(Composite parent, int style) {
super(parent, style);
new Label(this, SWT.NULL).setText("First Name");
new Label(this, SWT.NULL).setText("Last Name");
}
}

private static class Row extends Composite {
public Row(Composite parent, int style) {
super(parent, style);
firstName = new Text(this, SWT.NULL);
lastName = new Text(this, SWT.NULL);
}
public final Text firstName;
public final Text lastName;
}

// Where it all starts...

public static void main (String [] args) {
Display display = new Display ();
Shell shell = new Shell (display);
shell.setLayout(new FillLayout());

CompositeTable table = new CompositeTable(shell, SWT.NULL);
new Header(table, SWT.NULL); // Specify Header and Row
new Row(table, SWT.NULL);
table.setRunTime(true);
table.setNumRowsInCollection(swtCommitters.length);

// Note the JFace-like virtual table API
table.addRowContentProvider(new IRowContentProvider() {
public void refresh(CompositeTable sender,
int currentObjectOffset,
Control rowControl)
{
Row row = (Row) rowControl;

row.firstName.setText(swtCommitters[currentObjectOffset].fir st);
row.lastName.setText(swtCommitters[currentObjectOffset].last );
}
});

table.addRowFocusListener(new RowFocusAdapter() {
public void depart(CompositeTable sender,
int currentObjectOffset, Control rowControl) {
Row row = (Row) rowControl;

swtCommitters[currentObjectOffset].first = row.firstName.getText();
swtCommitters[currentObjectOffset].last = row.lastName.getText();
}
});

shell.setSize(500, 150);
shell.open ();
while (!shell.isDisposed()) {
if (!display.readAndDispatch ()) display.sleep ();
}
display.dispose ();

// Print the results
for (int i = 0; i < swtCommitters.length; i++) {
System.out.println(swtCommitters[i].first + " " +
swtCommitters[i].last);
}
}
}

If this can be (a) simplified, or (b) made cleaner by introducing a
CompositeTableItem, I'm interested. :-) (sincerely)

Your second point relates to the question of using factories versus
custom Composites. I actually wrote an earlier version of
CompositeTable this way, and I have two answers to this:

1) Using custom Composites to create custom SWT controls is the SWT way
of doing things (CCombo, etc...).

2) Using custom Composites encourages folks to design objects that can
stand alone. Using factories doesn't scale; you wind up with things like:

public static NameAndAddressControls
buildNameAndAddressComposite(Composite parent) {...}

and then to make matters worse, when you want to bind, you often wind up
with methods like:

public static void bindNameAndAddressControls(NameAndAddressControls
bigBagOSWTControls, Object person, String firstNameProperty, String
lastNameProperty, String address1Property, String cityProperty, String
stateProperty, String zipProperty) {...}

And where do you put these methods? They don't clearly belong to any
particular class.

So the resulting design isn't object oriented, isn't extensible, is hard
to follow, and so on.

So I'm actually pretty deeply concerned about folks doing RCP falling
into this trap. I've personally been there, done that, and have the
scars to prove it. Having an interface supplying public Control
createControl() is OK for a View, but I don't think it should be
generalized to all UI constructs.

What do I recommend doing instead?

Make an Address object that extends Composite. It can be used as the
row object inside a CompositeTable or it can stand on its own. It then
becomes the logical place for a bindAddress() method if you want one, or
if you want a strict MVC separation, you can bind in your controller
tier and just have getters for each of the SWT controls that need binding.


Best regards,

Dave Orme

PS: The above snippet and several others are in CVS. I'm working on
getting a real build out RSN.

>
> 
> CompositeTable table = new CompositeTable(parent, SWT.VIRTUAL | 
> SWT.BORDER);
> 
> // I like the class as a manager for the row, I just don't think it
> // should extend Composite by design
> // Adding this interface will remove all that reflection code
> interface ICompositeRow {
>   // Implementers are responsible for making getControl() return the
>   // created control
>   void createControl(CompositeTable table);
>   Control getControl();
> }
> 
> abstract class CompositeRow implements ICompositeRow {
>   Control control;
> 
>   Control getControl() {
>     return control;
>   }
> 
>   /** Sets the control returned by getControl */
>   void setControl(Control control) {
>     this.control = control;
>   }
> }
> 
> class MyHeader extends CompositeRow {
>   Label first;
>   Label last;
> 
>   void createControl(CompositeTable table) {
>     Composite composite = new Composite(table, SWT.NONE);
>     first = new Label(composite, SWT.NONE);
>     last = new Label(composite, SWT.NONE);
>     first.setText("First");
>     last.setText("Last");
>     setControl(composite);
>   }
> }
> 
> table.setHeaderProvider(new IRowProvider() {
>   ICompositeRow createRow() { return new MyHeader(); }
> });
> 
> class MyRow implements ICompositeRow {
>   Text first;
>   Text last;
> 
>   void createControl(CompositeTable table) {
>     Composite composite = new Composite(table, SWT.NONE);
>     first = new Text(composite, SWT.BORDER);
>     last = new Text(composite, SWT.BORDER);
>     setControl(composite);
>   }
> }
> 
> table.setRowProvider(new IRowProvider() {
>   ICompositeRow createRow() { return new MyRow(); }
> });
> 
> // The CompositeItem is basically the JFace wrapper around the content
> abstract class CompositeItem extends Item {
>   CompositeItem(CompositeTable table, int style) {
>     super(table, style);
>     table.addItem(this);
>   }
> 
>   CompositeItem(CompositeTable table, int style, int index) {
>     super(table, style);
>     table.addItem(this, index);
>   }
> 
>   // This property is managed by CompositeTable as it scrolls up
>   // and down
>   ICompositeRow row = null;
>   ICompositeRow getRow() { return row; }
>   void setRow(ICompositeRow row) {
>     if (this.row != null)
>       unhookListeners(this.row);
> 
>     this.row = row;
>     updateRow();
> 
>     if (row != null)
>       hookListeners(row);
>   }
> 
>   // These methods may be over-designed, but just a thought
>   // off the top of my head
>   // DataBinding would really help here
>   abstract void hookListeners(ICompositeRow row);
>   abstract void unhookListeners(ICompositeRow row);
>   abstract void updateRow();
> }
> 
> class MyItem extends CompositeItem implements Listener {
>   Name name = null;
> 
>   MyItem(CompositeTable table, int style) {
>     super(table, style);
>   }
> 
>   MyItem(CompositeTable table, int style, int index, Name name) {
>     super(table, style, index);
>   }
> 
>   Name getName() { return name; }
>   void setName(Name name) {
>     this.name = name;
>     updateRow();
>   }
> 
>   void hookListeners(ICompositeRow row) {
>     MyRow r = (MyRow) row;
>     r.first.addListener(SWT.Modify, this);
>     r.last.addListener(SWT.Modify, this);
>   }
> 
>   void unhookListeners(ICompositeRow row) {
>     MyRow r = (MyRow) row;
>     r.first.removeListener(SWT.Modify, this);
>     r.last.removeListener(SWT.Modify, this);
>   }
> 
>   void updateRow() {
>     MyRow r = (MyRow) getRow();
>     if (r == null) return;
>     r.first.setText(name == null ? "" : name.getFirst());
>     r.last.setText(name == null ? "" : name.getLast());
>   }
> 
>   void handleEvent(Event e) {
>     if (name == null) return;
> 
>     MyRow row = (MyRow) getRow();
>     if (e.widget == row.first)
>       name.setFirst(row.first.getText());
>     else if (e.widget == row.last)
>       name.setLast(row.last.getText());
>   }
> }
> 
> table.setItemProvider(new ICompositeItemProvider() {
>   CompositeItem createItem(CompositeTable table, int style, int index) {
>     return new MyItem(table, style, index);
>   }
> });
> 
> table.addListener(SWT.SetData, new Listener() {
>   void handleEvent(Event e) {
>     MyItem item = (MyItem) e.item;
>     int index = table.indexOf(item);
>     item.setName(Names.get(index));
>   }
> });
> 
> table.setItemCount(Names.getCount());
> 
> 

>
> This is just a rough sketch of what I had in mind.
>
>> 1) The *Item concept in SWT mainly represents what *data* will be
>> placed in the specified columns, along with some layout information
>> (width, etc).
>>
>> 2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
>> items for *all* rows that have been displayed and then never destroys
>> them.
>
> As outlined above, an Item is a separate concept from a Row. The item
> maps to the data, where the Row maps to the visible display.
>
>> If I called it setItemCount, this would imply that if you
>> setItemCount(1000000), that there would be a million
>> CompositeTableItem objects somewhere, which simply isn't true.
>
> Not necessarily. This behavior could be emulated and items created on
> the fly as they are needed for display by the ICompositeItemProvider,
> and initialized by the SWT.SetData listener.
>
> It would also be useful to have SWT.VIRTUAL be an option instead of a
> given. This would allow users to just instantiate their items as needed
> for small collections, which would result in simpler code:
>
>
> for (int i = 0; i < Names.getCount(); i++)
>   new MyItem(table, SWT.NONE).setName(Names.get(i));
> 

>
>>> I don't like the design-mode / active-mode paradigm.
>>
>> Neither do I.
>>
>> There are two reasons this exists: One major goal I had when creating
>> CompositeTable is that it would be simple to use within Visual Editor.
>>
>> I could use Beans.isDesignTime() in the control and maybe I should do
>> that, but I wanted the control behave inside VE exactly the way it
>> behaves at run-time. This way you can more easily learn to use the
>> control by changing the properties interactively in VE and watching
>> what happens.
>>
>> The only way to accomplish this is to have a property that explicitly
>> switches the control from design-time behavior to run-time behavior.
>>
>> The second reason is that JavaBeans isn't in Foundation profile. So
>> in order to support Foundation, I can't use Beans.isDesignTime().
>>
>> But maybe this property was a bad idea.
>>
>> I'd be happy for feedback on this. What do folks think?
>>
>
> Perhaps make the property false by default? The design changes I'm
> suggesting would not prevent this option, but it is a little jarring to
> have this setDesignTime(false) method call in the middle of my code.
>
>>> Then there is the use of reflection. Although I recognize that Dave
>>> Orme (who authored the control) would be quite comfortable with
>>> reflection, given his role in VE and data binding, I am nonetheless
>>> uncomfortable with it. Using reflection is a performance hit, is
>>> brittle, and really isn't necessary if we just invent an interface to
>>> replace it (ICompositeRowBuilder). Moreover it makes adoption into
>>> SWT impossible since (as I understand it) reflection is not available
>>> in the CDC-1.0/Foundation-1.0 runtime environment.
>>
>> There is a really good question here, but a few misconceptions too.
>> I'll clear away the misconceptions first, and then we can hopefully
>> tackle the underlying question more productively:
>>
>> 1) On Foundation support: reflection is there but not dynamic proxies
>> or JavaBean support.
>
> Good to know
>
>>
>> 2) Regarding performance, reflection is only used to construct new row
>> controls. But once a row control is constructed, it is never
>> destroyed until the entire CompositeTable control is destroyed.
>> (Instead, CompositeTable recycles row objects.) So if your table has
>> 20 rows of data in it, there will be exactly 20 reflection calls the
>> first time your data is displayed and no more reflection calls after
>> that. Since reflection is never used any more after the row controls
>> are constructed, performance just isn't an issue here.
>
> True, but a regular old java interface like IRowProvider is much more
> comfortable to Java programmers than duck typing.
>
>> 3) I don't understand how reflection is brittle in this case?
>
> It excludes the possibility of other constructor signatures, such as
> MyCompositeRow(CompositeTable table) where the style bit is implicit.
> Although considered bad form in SWT, this is a legitimate choice for the
> developer.
>
>> Now on to the underlying question (the whole reason I use reflection
>> to begin with):
>>
>>> And I REALLY don't like being forced to extend composite for my rows,
>>> when we could just define an interface that creates and manages a
>>> composite instead. This is a very Swing way of using SWT.
>>
>> As stated above, a design goal for CompositeTable was to be able to
>> edit the table visually using Visual Editor. Visual Editor knows how
>> to edit a custom Composite, but not how to edit a JFace-like
>> createControl() UI factory.
>
> The JFace createControl() factory paradigm is pervasive throughout the
> platform. I think the "knows how to edit" use case really belongs in
> VE, not in each control we hope to use in VE.
>
>> However, I would like to be able to accommodate folks that would
>> prefer to use an interface. If someone can propose an API that makes
>> sense and doesn't lose the VE support, I'd be very glad to listen.
>
> Perhaps you could point me to some HOWTO's or tutorials for teaching VE
> how to design custom controls, and I'll help you work on it.
>
>>> It would also seem more appropriate to use SWT.SetData listeners like
>>> the other virtual controls instead of addRowContentProvider.
>>
>> Again, it's a possibility to try to mimic the SWT names, but don't you
>> feel that folks will be confused here?
>
> That's a question for the bystanders!
>
> Maybe it would help if we following Steve Northover's advice and set the
> SWT.SMART bit on the CompositeTable. :)
>
>> In CompositeTable's event, one normally doesn't set data into some
>> *Item object, but rather sets data into real SWT controls in your row
>> object or possibly uses data binding to bind those controls to a
>> domain model object.
>
> Sorry, I should have explained that in my original post. In my proposed
> design the concrete CompositeItem subclass is responsible for populating
> the ICompositeRow fields and managing the binding between those
> controls. This is a departure from SWT conventions, but as you say this
> is a different beast, and I felt it was the least "weird" of approaches.
> Your mileage my vary.
>
>> What CompositeTable does here seems closer conceptually to the JFace
>> content provider concept, which is why this name was chosen.
>>
>> I'm willing to rename this, but I'm concerned about confusion.
>
> To me this design feels a lot clearer and simpler, but I acknowledge
> that this may be confusing to others.
>
>> In balance, CompositeTable tries to reflect and synthesize ideas from
>> all of SWT + JFace + Visual Editor + Eclipse Data binding APIs. My
>> hope is that this will make folks more productive and result in more
>> maintainable applications.
>
> Thanks Dave for taking the time to respond.
>
> Matthew
Re: Reactions to CompositeTable API [message #19048 is a reply to message #18982] Fri, 01 December 2006 17:58 Go to previous messageGo to next message
Chris Gross is currently offline Chris GrossFriend
Messages: 253
Registered: July 2009
Senior Member
Hi Matt,

Just to be clear, I didn't mean to imply that what you were asking was
unreasonable. Not at all. I can see how your changes would make sense
(though admittedly I'm not well versed in CompositeTable and haven't
looked hard at your changes). I just wanted to figure out what about
CompositeTable was really exciting you (exciting enough that you are
willing to spend time talking about these changes). I was just curious
is all.

Regards,
-Chris

Matthew Hall wrote:
> Chris Gross wrote:
>> Can I ask a (perhaps dumb) question? You seem to want to change a lot
>> of the CompositeTable API and make it fit in better with SWT, etc.
>
> I'm not trying to rock the boat here. David Orme himself said that he
> want to avoid confusing users. I'm making these suggestions because I
> think it will make the control simpler and more intuitive. And I'm not
> suggesting that my ideas are the best--I'm trying to get a dialog going.
>
>> With all these changes wouldn't the end result be much like a regular
>> SWT Table that is populated with widgets using TableEditors (except
>> that the editors are only created on visible rows)? In other words,
>> it sounds like alot of what you don't like is what makes
>> CompositeTable unique.
>
> Not really. I'm suggesting changes to the API to make what
> CompositeTable does more accessible to SWT programmers. The
> reservations I have are:
>
> * I dislike reflection because however you use reflection becomes de
> facto API, except the compiler can't check for bad usage. Who knows if
> somebody will refactor your Row class down the road, not knowing it
> *has* to have a (Composite, int) constructor? The compiler will *never*
> catch this. A documented interface instead of reflection will avoid
> this problem. Besides, it may be possible to just have the default
> IRowProvider perform this exact behavior so that current CompositeTable
> users can just keep doing prototyping if they prefer.
> * SWT programmers are used to working with *Items. Working with items
> the non-virtual way is much easier than the virtual way, and I would
> like an option between the two.
> * Renaming some of the API (numRowsInCollection == itemCount) to match
> SWT naming conventions will make using this control more intuitive.
>
>> What is the feature (or features) from CompositeTable that you think
>> are the killer (i.e. killer in a good way ;)?
>
> * The ability to use controls at all times, instead of having to click
> the cell to bring up the editor.
> * The ability to lay out those controls any way you like within the row
> if the standard left-to-right columnar layout doesn't suit you.
>
> I'm willing to program these changes myself and submit a patch. I just
> wanted to see what the general consensus is before I started.
>
> Matt
Re: Reactions to CompositeTable API [message #19061 is a reply to message #18982] Fri, 01 December 2006 18:24 Go to previous messageGo to next message
Thomas Schindl is currently offline Thomas SchindlFriend
Messages: 5487
Registered: July 2009
Senior Member
[...]
> * The ability to use controls at all times, instead of having to click
> the cell to bring up the editor.

TableViewer/TreeViewer will hopefully also support this kind of feature
in 3.3 timeframe (I'm working on it currently). Tabing support is
already in the latest nightly build if you are interested.

https://bugs.eclipse.org/bugs/show_bug.cgi?id=166383
Usage is shown in this snippet:
http://dev.eclipse.org/viewcvs/index.cgi/%7Echeckout%7E/org. eclipse.jface.snippets/Eclipse%20JFace%20Snippets/org/eclips e/jface/snippets/viewers/Snippet025TabEditing.java

Keyboard navigation in Tables will follow in 3.3M4 or 3.3M5.

Tom

[...]
Re: Reactions to CompositeTable API [message #19240 is a reply to message #18982] Fri, 01 December 2006 19:31 Go to previous messageGo to next message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
1) THANKS again for wanting to contribute.

2) I think I replied to your other concerns in the other reply except
for one: reflection.

To this, I reply: SWT controls will *never* deviate from having (parent,
style) as long as Steve Northover is SWT lead. ;-)


Regards,

Dave Orme

Matthew Hall wrote:
> Chris Gross wrote:
>> Can I ask a (perhaps dumb) question? You seem to want to change a lot
>> of the CompositeTable API and make it fit in better with SWT, etc.
>
> I'm not trying to rock the boat here. David Orme himself said that he
> want to avoid confusing users. I'm making these suggestions because I
> think it will make the control simpler and more intuitive. And I'm not
> suggesting that my ideas are the best--I'm trying to get a dialog going.
>
>> With all these changes wouldn't the end result be much like a regular
>> SWT Table that is populated with widgets using TableEditors (except
>> that the editors are only created on visible rows)? In other words,
>> it sounds like alot of what you don't like is what makes
>> CompositeTable unique.
>
> Not really. I'm suggesting changes to the API to make what
> CompositeTable does more accessible to SWT programmers. The
> reservations I have are:
>
> * I dislike reflection because however you use reflection becomes de
> facto API, except the compiler can't check for bad usage. Who knows if
> somebody will refactor your Row class down the road, not knowing it
> *has* to have a (Composite, int) constructor? The compiler will *never*
> catch this. A documented interface instead of reflection will avoid
> this problem. Besides, it may be possible to just have the default
> IRowProvider perform this exact behavior so that current CompositeTable
> users can just keep doing prototyping if they prefer.
> * SWT programmers are used to working with *Items. Working with items
> the non-virtual way is much easier than the virtual way, and I would
> like an option between the two.
> * Renaming some of the API (numRowsInCollection == itemCount) to match
> SWT naming conventions will make using this control more intuitive.
>
>> What is the feature (or features) from CompositeTable that you think
>> are the killer (i.e. killer in a good way ;)?
>
> * The ability to use controls at all times, instead of having to click
> the cell to bring up the editor.
> * The ability to lay out those controls any way you like within the row
> if the standard left-to-right columnar layout doesn't suit you.
>
> I'm willing to program these changes myself and submit a patch. I just
> wanted to see what the general consensus is before I started.
>
> Matt
Re: Reactions to CompositeTable API [message #19263 is a reply to message #19240] Fri, 01 December 2006 20:53 Go to previous messageGo to next message
Matthew Hall is currently offline Matthew HallFriend
Messages: 368
Registered: July 2009
Senior Member
> To this, I reply: SWT controls will *never* deviate from having (parent,
> style) as long as Steve Northover is SWT lead. ;-)

Touché
Re: Reactions to CompositeTable API [message #20296 is a reply to message #19061] Sun, 10 December 2006 06:06 Go to previous messageGo to next message
Eclipse UserFriend
Originally posted by: alnospammajor.noboxspamspoon.com

Tom Schindl wrote:
> [...]
>> * The ability to use controls at all times, instead of having to click
>> the cell to bring up the editor.
>
> TableViewer/TreeViewer will hopefully also support this kind of feature
> in 3.3 timeframe (I'm working on it currently). Tabing support is

any timeframe on this as yet? is there a bug number that i can track?
i'd be happy to test any functionality you put out there. if this is
done comprehensively (there's a few life cycle events that i've pointed
out in discussions on CTableTree), it may be enough for my current needs.

thx,

al
Re: Reactions to CompositeTable API [message #20306 is a reply to message #20296] Sun, 10 December 2006 11:25 Go to previous messageGo to next message
Thomas Schindl is currently offline Thomas SchindlFriend
Messages: 5487
Registered: July 2009
Senior Member
Hi Al,

I hope you got me right. Table/TreeViewer will not support to use
controls and will keep the editor activation approach because of
performance reasons although there's a feature request for this
(https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977).

Keyboard navigation and more lifecycle events are discussed in:
- https://bugs.eclipse.org/bugs/show_bug.cgi?id=151377
- https://bugs.eclipse.org/bugs/show_bug.cgi?id=151295
- https://bugs.eclipse.org/bugs/show_bug.cgi?id=167325

I can not commit to any date because I'm not the one to decide whether
my way of thinking is appropriate although I think I can convince
Boris/Tod (JFace-Leads). But the more votes and comments the two bugs
will get the better the solution will be the above bugs hold a dump of
my brain how I could imagine this could work.

If they follow me I will provide support in M5 but if this is not
possible because of whatever reason there won't be support in 3.3
because in M5 the API is frozen and I'll have no chance to get this new
API in.

By the way with M4 JFace will provide a widget independent
AbstractTableViewer which Nebula components can subclass for their
needs. Maybe the above bugs (151295, 167325) will modify the API
slightly but that's not a big deal for implementors I think.

Tom

Al Major schrieb:
> Tom Schindl wrote:
>> [...]
>>> * The ability to use controls at all times, instead of having to click
>>> the cell to bring up the editor.
>>
>> TableViewer/TreeViewer will hopefully also support this kind of feature
>> in 3.3 timeframe (I'm working on it currently). Tabing support is
>
> any timeframe on this as yet? is there a bug number that i can
> track? i'd be happy to test any functionality you put out there. if this
> is done comprehensively (there's a few life cycle events that i've
> pointed out in discussions on CTableTree), it may be enough for my
> current needs.
>
> thx,
>
> al
Re: Reactions to CompositeTable API [message #20316 is a reply to message #18758] Mon, 11 December 2006 02:23 Go to previous messageGo to next message
Eclipse UserFriend
Originally posted by: alnospammajor.noboxspamspoon.com

David J. Orme wrote:
>
> 2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
> items for *all* rows that have been displayed and then never destroys them.
>
> In contrast, the row objects in CompositeTable correspond to exactly the
> SWT controls that are visible. Once a row becomes invisible, it ceases
> to exist as far as CompositeTable's layout is concerned. If topRow() is
> 0, the visible table height is 20 rows, and numRowsInCollection is 25,
> CompositeTable still only maintains row objects for the top 20 rows. Not
> only that, but as soon as the user scrolls forward one row, the top row
> control is immediately discarded, a new one is created representing row
> 21, and all the controls in the middle are shifted up. (In practice,
> CompositeTable recycles the row objects, so there is no performance loss
> from creating and disposing controls.)
>
> I could rename the "row" concept to "Item", but I'm concerned that this
> would be confusing. They just are really different things, and behave
> completely differently.
>

the recycling of controls is a great feature.

is there a reasonable way to map a JFace style viewer (with items) onto
CompositeTable rows? like Matthew, i quite like the specific style of
MVC used by JFace.

my use case requires GEF viewers embedded in table cells. all rows have
the same height (which needs to be set). but there is a need to control
the order in which viewers in different columns of the same row are
initialized.

regards,

al
Re: Reactions to CompositeTable API [message #20324 is a reply to message #20306] Mon, 11 December 2006 02:24 Go to previous messageGo to next message
Eclipse UserFriend
Originally posted by: alnospammajor.noboxspamspoon.com

sorry, i did misunderstand you.

https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977

is the feature that i'm looking for (and i just put in a vote for it).
the other features are not directly applicable.

i'll keep track of this feature to see if there's any progress on it.

regards,

al


Tom Schindl wrote:
> Hi Al,
>
> I hope you got me right. Table/TreeViewer will not support to use
> controls and will keep the editor activation approach because of
> performance reasons although there's a feature request for this
> (https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977).
>
> Keyboard navigation and more lifecycle events are discussed in:
> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151377
> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151295
> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=167325
>
> I can not commit to any date because I'm not the one to decide whether
> my way of thinking is appropriate although I think I can convince
> Boris/Tod (JFace-Leads). But the more votes and comments the two bugs
> will get the better the solution will be the above bugs hold a dump of
> my brain how I could imagine this could work.
>
> If they follow me I will provide support in M5 but if this is not
> possible because of whatever reason there won't be support in 3.3
> because in M5 the API is frozen and I'll have no chance to get this new
> API in.
>
> By the way with M4 JFace will provide a widget independent
> AbstractTableViewer which Nebula components can subclass for their
> needs. Maybe the above bugs (151295, 167325) will modify the API
> slightly but that's not a big deal for implementors I think.
>
> Tom
>
> Al Major schrieb:
>> Tom Schindl wrote:
>>> [...]
>>>> * The ability to use controls at all times, instead of having to click
>>>> the cell to bring up the editor.
>>>
>>> TableViewer/TreeViewer will hopefully also support this kind of feature
>>> in 3.3 timeframe (I'm working on it currently). Tabing support is
>>
>> any timeframe on this as yet? is there a bug number that i can
>> track? i'd be happy to test any functionality you put out there. if
>> this is done comprehensively (there's a few life cycle events that
>> i've pointed out in discussions on CTableTree), it may be enough for
>> my current needs.
>>
>> thx,
>>
>> al
Re: Reactions to CompositeTable API [message #20334 is a reply to message #20324] Mon, 11 December 2006 09:10 Go to previous messageGo to next message
Thomas Schindl is currently offline Thomas SchindlFriend
Messages: 5487
Registered: July 2009
Senior Member
Hi,

If nobody else than me is working on this feature, don't expect any
support in 3.3 timeframe if this will ever be addressed by JFace.

Tom

Al Major schrieb:
> sorry, i did misunderstand you.
>
> https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977
>
> is the feature that i'm looking for (and i just put in a vote for it).
> the other features are not directly applicable.
>
> i'll keep track of this feature to see if there's any progress on it.
>
> regards,
>
> al
>
>
> Tom Schindl wrote:
>> Hi Al,
>>
>> I hope you got me right. Table/TreeViewer will not support to use
>> controls and will keep the editor activation approach because of
>> performance reasons although there's a feature request for this
>> (https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977).
>>
>> Keyboard navigation and more lifecycle events are discussed in:
>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151377
>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151295
>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=167325
>>
>> I can not commit to any date because I'm not the one to decide whether
>> my way of thinking is appropriate although I think I can convince
>> Boris/Tod (JFace-Leads). But the more votes and comments the two bugs
>> will get the better the solution will be the above bugs hold a dump of
>> my brain how I could imagine this could work.
>>
>> If they follow me I will provide support in M5 but if this is not
>> possible because of whatever reason there won't be support in 3.3
>> because in M5 the API is frozen and I'll have no chance to get this
>> new API in.
>>
>> By the way with M4 JFace will provide a widget independent
>> AbstractTableViewer which Nebula components can subclass for their
>> needs. Maybe the above bugs (151295, 167325) will modify the API
>> slightly but that's not a big deal for implementors I think.
>>
>> Tom
>>
>> Al Major schrieb:
>>> Tom Schindl wrote:
>>>> [...]
>>>>> * The ability to use controls at all times, instead of having to click
>>>>> the cell to bring up the editor.
>>>>
>>>> TableViewer/TreeViewer will hopefully also support this kind of feature
>>>> in 3.3 timeframe (I'm working on it currently). Tabing support is
>>>
>>> any timeframe on this as yet? is there a bug number that i can
>>> track? i'd be happy to test any functionality you put out there. if
>>> this is done comprehensively (there's a few life cycle events that
>>> i've pointed out in discussions on CTableTree), it may be enough for
>>> my current needs.
>>>
>>> thx,
>>>
>>> al
Re: Reactions to CompositeTable API [message #20344 is a reply to message #20334] Mon, 11 December 2006 13:08 Go to previous messageGo to next message
Eclipse UserFriend
Originally posted by: alnospammajor.noboxspamspoon.com

i'm happy to contribute patches if you're looking for help with it.

Tom Schindl wrote:
> Hi,
>
> If nobody else than me is working on this feature, don't expect any
> support in 3.3 timeframe if this will ever be addressed by JFace.
>
> Tom
>
> Al Major schrieb:
>> sorry, i did misunderstand you.
>>
>> https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977
>>
>> is the feature that i'm looking for (and i just put in a vote for it).
>> the other features are not directly applicable.
>>
>> i'll keep track of this feature to see if there's any progress on it.
>>
>> regards,
>>
>> al
>>
>>
>> Tom Schindl wrote:
>>> Hi Al,
>>>
>>> I hope you got me right. Table/TreeViewer will not support to use
>>> controls and will keep the editor activation approach because of
>>> performance reasons although there's a feature request for this
>>> (https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977).
>>>
>>> Keyboard navigation and more lifecycle events are discussed in:
>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151377
>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151295
>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=167325
>>>
>>> I can not commit to any date because I'm not the one to decide whether
>>> my way of thinking is appropriate although I think I can convince
>>> Boris/Tod (JFace-Leads). But the more votes and comments the two bugs
>>> will get the better the solution will be the above bugs hold a dump of
>>> my brain how I could imagine this could work.
>>>
>>> If they follow me I will provide support in M5 but if this is not
>>> possible because of whatever reason there won't be support in 3.3
>>> because in M5 the API is frozen and I'll have no chance to get this
>>> new API in.
>>>
>>> By the way with M4 JFace will provide a widget independent
>>> AbstractTableViewer which Nebula components can subclass for their
>>> needs. Maybe the above bugs (151295, 167325) will modify the API
>>> slightly but that's not a big deal for implementors I think.
>>>
>>> Tom
>>>
>>> Al Major schrieb:
>>>> Tom Schindl wrote:
>>>>> [...]
>>>>>> * The ability to use controls at all times, instead of having to click
>>>>>> the cell to bring up the editor.
>>>>> TableViewer/TreeViewer will hopefully also support this kind of feature
>>>>> in 3.3 timeframe (I'm working on it currently). Tabing support is
>>>> any timeframe on this as yet? is there a bug number that i can
>>>> track? i'd be happy to test any functionality you put out there. if
>>>> this is done comprehensively (there's a few life cycle events that
>>>> i've pointed out in discussions on CTableTree), it may be enough for
>>>> my current needs.
>>>>
>>>> thx,
>>>>
>>>> al
Re: Reactions to CompositeTable API [message #20354 is a reply to message #20344] Mon, 11 December 2006 15:26 Go to previous messageGo to next message
Thomas Schindl is currently offline Thomas SchindlFriend
Messages: 5487
Registered: July 2009
Senior Member
Hi,

if you want to work on it give it a go. I'll support you as much as I
can but keep in mind that there are also
SWT-Problems(TableEditor/TreeEditor) who are a show stoppers for placing
controls in Table/Tree
( https://bugs.eclipse.org/bugs/buglist.cgi?query_format=advan ced&short_desc_type=allwordssubstr&short_desc=&c lassification=Eclipse&product=Platform&component=SWT &long_desc_type=allwordssubstr&long_desc=TableEditor &bug_file_loc_type=allwordssubstr&bug_file_loc=& status_whiteboard_type=allwordssubstr&status_whiteboard= &keywords_type=allwords&keywords=&bug_status=NEW &bug_status=ASSIGNED&emailtype1=substring&email1 =&emailtype2=substring&email2=&bugidtype=include &bug_id=&votes=&chfieldfrom=&chfieldto=Now&a mp;chfieldvalue=&cmdtype=doit&order=Reuse+same+sort+ as+last+time&field0-0-0=noop&type0-0-0=noop&valu e0-0-0=).

Until those bugs are not resolved I think placing Controls in
tables/trees is not really interesting for JFace components.

As already said time until API freeze is in about 8 weeks but that
doesn't mean that we could not collect ideas, code fragments, ... .

I have to admit that I've never looked into CompositeTable but maybe it
would be a better idea to provide a JFace-Viewer-API for it? But if I
read David's comments from above this doesn't seem to be possible.

Tom

Al Major schrieb:
> i'm happy to contribute patches if you're looking for help with it.
>
> Tom Schindl wrote:
>> Hi,
>>
>> If nobody else than me is working on this feature, don't expect any
>> support in 3.3 timeframe if this will ever be addressed by JFace.
>>
>> Tom
>>
>> Al Major schrieb:
>>> sorry, i did misunderstand you.
>>>
>>> https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977
>>>
>>> is the feature that i'm looking for (and i just put in a vote for it).
>>> the other features are not directly applicable.
>>>
>>> i'll keep track of this feature to see if there's any progress on it.
>>>
>>> regards,
>>>
>>> al
>>>
>>>
>>> Tom Schindl wrote:
>>>> Hi Al,
>>>>
>>>> I hope you got me right. Table/TreeViewer will not support to use
>>>> controls and will keep the editor activation approach because of
>>>> performance reasons although there's a feature request for this
>>>> (https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977).
>>>>
>>>> Keyboard navigation and more lifecycle events are discussed in:
>>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151377
>>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151295
>>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=167325
>>>>
>>>> I can not commit to any date because I'm not the one to decide whether
>>>> my way of thinking is appropriate although I think I can convince
>>>> Boris/Tod (JFace-Leads). But the more votes and comments the two bugs
>>>> will get the better the solution will be the above bugs hold a dump of
>>>> my brain how I could imagine this could work.
>>>>
>>>> If they follow me I will provide support in M5 but if this is not
>>>> possible because of whatever reason there won't be support in 3.3
>>>> because in M5 the API is frozen and I'll have no chance to get this
>>>> new API in.
>>>>
>>>> By the way with M4 JFace will provide a widget independent
>>>> AbstractTableViewer which Nebula components can subclass for their
>>>> needs. Maybe the above bugs (151295, 167325) will modify the API
>>>> slightly but that's not a big deal for implementors I think.
>>>>
>>>> Tom
>>>>
>>>> Al Major schrieb:
>>>>> Tom Schindl wrote:
>>>>>> [...]
>>>>>>> * The ability to use controls at all times, instead of having to
>>>>>>> click
>>>>>>> the cell to bring up the editor.
>>>>>> TableViewer/TreeViewer will hopefully also support this kind of
>>>>>> feature
>>>>>> in 3.3 timeframe (I'm working on it currently). Tabing support is
>>>>> any timeframe on this as yet? is there a bug number that i can
>>>>> track? i'd be happy to test any functionality you put out there. if
>>>>> this is done comprehensively (there's a few life cycle events that
>>>>> i've pointed out in discussions on CTableTree), it may be enough for
>>>>> my current needs.
>>>>>
>>>>> thx,
>>>>>
>>>>> al
Re: Reactions to CompositeTable API [message #20364 is a reply to message #20354] Tue, 12 December 2006 03:03 Go to previous messageGo to next message
Eclipse UserFriend
Originally posted by: alnospammajor.noboxspamspoon.com

hmm. it's disappointing that TableEditor appears to have display bugs.
however i'm guessing that it has been more comprehensively tested than
any of the other options (which probably have display bugs that haven't
been reported yet :-).

of the various options CTableTree does everything i need at the moment
(ok so i have to hack it a bit to accomodate some life cycle events),
except for one thing: support for ITreePathContentProvider. It was
waiting on:

https://bugs.eclipse.org/bugs/show_bug.cgi?id=154329

but perhaps now it's waiting on

https://bugs.eclipse.org/bugs/show_bug.cgi?id=167323

jeremy can probably comment on this.

the last time i looked at the support for ITreePathContentProvider,
there were some peculiarities about the way the JFace viewer was using
the interface (it appeared to be bypassing it). perhaps it's been fixed
by now.

the only other weaknesses i have seen in CTableTree relative to other
options.
a) there were some display artifacts (flicker, bug in column redraw). i
haven't gotten around to creating a simple test case that replicates
these. this is just part of the maturing process (but the reason it
makes sense to use something like the TableEditor solution which has
already been used quite a bit).
b) it would be nice to have control life cycle that only keeps controls
around for the visible part of the tabletree (reuse these controls a la
CompositeTable).
c) it isn't in SWT/JFace (yet :-).

regards,

al


Tom Schindl wrote:
> Hi,
>
> if you want to work on it give it a go. I'll support you as much as I
> can but keep in mind that there are also
> SWT-Problems(TableEditor/TreeEditor) who are a show stoppers for placing
> controls in Table/Tree
> ( https://bugs.eclipse.org/bugs/buglist.cgi?query_format=advan ced&short_desc_type=allwordssubstr&short_desc=&c lassification=Eclipse&product=Platform&component=SWT &long_desc_type=allwordssubstr&long_desc=TableEditor &bug_file_loc_type=allwordssubstr&bug_file_loc=& status_whiteboard_type=allwordssubstr&status_whiteboard= &keywords_type=allwords&keywords=&bug_status=NEW &bug_status=ASSIGNED&emailtype1=substring&email1 =&emailtype2=substring&email2=&bugidtype=include &bug_id=&votes=&chfieldfrom=&chfieldto=Now&a mp;chfieldvalue=&cmdtype=doit&order=Reuse+same+sort+ as+last+time&field0-0-0=noop&type0-0-0=noop&valu e0-0-0=).
>
> Until those bugs are not resolved I think placing Controls in
> tables/trees is not really interesting for JFace components.
>
> As already said time until API freeze is in about 8 weeks but that
> doesn't mean that we could not collect ideas, code fragments, ... .
>
> I have to admit that I've never looked into CompositeTable but maybe it
> would be a better idea to provide a JFace-Viewer-API for it? But if I
> read David's comments from above this doesn't seem to be possible.
>
> Tom
>
> Al Major schrieb:
>> i'm happy to contribute patches if you're looking for help with it.
>>
>> Tom Schindl wrote:
>>> Hi,
>>>
>>> If nobody else than me is working on this feature, don't expect any
>>> support in 3.3 timeframe if this will ever be addressed by JFace.
>>>
>>> Tom
>>>
>>> Al Major schrieb:
>>>> sorry, i did misunderstand you.
>>>>
>>>> https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977
>>>>
>>>> is the feature that i'm looking for (and i just put in a vote for it).
>>>> the other features are not directly applicable.
>>>>
>>>> i'll keep track of this feature to see if there's any progress on it.
>>>>
>>>> regards,
>>>>
>>>> al
>>>>
>>>>
>>>> Tom Schindl wrote:
>>>>> Hi Al,
>>>>>
>>>>> I hope you got me right. Table/TreeViewer will not support to use
>>>>> controls and will keep the editor activation approach because of
>>>>> performance reasons although there's a feature request for this
>>>>> (https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977).
>>>>>
>>>>> Keyboard navigation and more lifecycle events are discussed in:
>>>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151377
>>>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151295
>>>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=167325
>>>>>
>>>>> I can not commit to any date because I'm not the one to decide whether
>>>>> my way of thinking is appropriate although I think I can convince
>>>>> Boris/Tod (JFace-Leads). But the more votes and comments the two bugs
>>>>> will get the better the solution will be the above bugs hold a dump of
>>>>> my brain how I could imagine this could work.
>>>>>
>>>>> If they follow me I will provide support in M5 but if this is not
>>>>> possible because of whatever reason there won't be support in 3.3
>>>>> because in M5 the API is frozen and I'll have no chance to get this
>>>>> new API in.
>>>>>
>>>>> By the way with M4 JFace will provide a widget independent
>>>>> AbstractTableViewer which Nebula components can subclass for their
>>>>> needs. Maybe the above bugs (151295, 167325) will modify the API
>>>>> slightly but that's not a big deal for implementors I think.
>>>>>
>>>>> Tom
>>>>>
>>>>> Al Major schrieb:
>>>>>> Tom Schindl wrote:
>>>>>>> [...]
>>>>>>>> * The ability to use controls at all times, instead of having to
>>>>>>>> click
>>>>>>>> the cell to bring up the editor.
>>>>>>> TableViewer/TreeViewer will hopefully also support this kind of
>>>>>>> feature
>>>>>>> in 3.3 timeframe (I'm working on it currently). Tabing support is
>>>>>> any timeframe on this as yet? is there a bug number that i can
>>>>>> track? i'd be happy to test any functionality you put out there. if
>>>>>> this is done comprehensively (there's a few life cycle events that
>>>>>> i've pointed out in discussions on CTableTree), it may be enough for
>>>>>> my current needs.
>>>>>>
>>>>>> thx,
>>>>>>
>>>>>> al
Re: Reactions to CompositeTable API [message #20375 is a reply to message #20354] Tue, 12 December 2006 03:15 Go to previous messageGo to next message
Eclipse UserFriend
Originally posted by: alnospammajor.noboxspamspoon.com

i think Jeremy is still planning to re-use the updated JFace treeviewer
as the basis for CTableTreeViewer. is that still correct, jeremy? if
that's so, perhaps it would be best to introduce any changes into
CTableTree and use that as the basis for changes to the base class in
the 3.4 timeframe?

regards,

al


Tom Schindl wrote:
> Hi,
>
> if you want to work on it give it a go. I'll support you as much as I
> can but keep in mind that there are also
> SWT-Problems(TableEditor/TreeEditor) who are a show stoppers for placing
> controls in Table/Tree
> ( https://bugs.eclipse.org/bugs/buglist.cgi?query_format=advan ced&short_desc_type=allwordssubstr&short_desc=&c lassification=Eclipse&product=Platform&component=SWT &long_desc_type=allwordssubstr&long_desc=TableEditor &bug_file_loc_type=allwordssubstr&bug_file_loc=& status_whiteboard_type=allwordssubstr&status_whiteboard= &keywords_type=allwords&keywords=&bug_status=NEW &bug_status=ASSIGNED&emailtype1=substring&email1 =&emailtype2=substring&email2=&bugidtype=include &bug_id=&votes=&chfieldfrom=&chfieldto=Now&a mp;chfieldvalue=&cmdtype=doit&order=Reuse+same+sort+ as+last+time&field0-0-0=noop&type0-0-0=noop&valu e0-0-0=).
>
> Until those bugs are not resolved I think placing Controls in
> tables/trees is not really interesting for JFace components.
>
> As already said time until API freeze is in about 8 weeks but that
> doesn't mean that we could not collect ideas, code fragments, ... .
>
> I have to admit that I've never looked into CompositeTable but maybe it
> would be a better idea to provide a JFace-Viewer-API for it? But if I
> read David's comments from above this doesn't seem to be possible.
>
> Tom
>
> Al Major schrieb:
>> i'm happy to contribute patches if you're looking for help with it.
>>
>> Tom Schindl wrote:
>>> Hi,
>>>
>>> If nobody else than me is working on this feature, don't expect any
>>> support in 3.3 timeframe if this will ever be addressed by JFace.
>>>
>>> Tom
>>>
>>> Al Major schrieb:
>>>> sorry, i did misunderstand you.
>>>>
>>>> https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977
>>>>
>>>> is the feature that i'm looking for (and i just put in a vote for it).
>>>> the other features are not directly applicable.
>>>>
>>>> i'll keep track of this feature to see if there's any progress on it.
>>>>
>>>> regards,
>>>>
>>>> al
>>>>
>>>>
>>>> Tom Schindl wrote:
>>>>> Hi Al,
>>>>>
>>>>> I hope you got me right. Table/TreeViewer will not support to use
>>>>> controls and will keep the editor activation approach because of
>>>>> performance reasons although there's a feature request for this
>>>>> (https://bugs.eclipse.org/bugs/show_bug.cgi?id=36977).
>>>>>
>>>>> Keyboard navigation and more lifecycle events are discussed in:
>>>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151377
>>>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=151295
>>>>> - https://bugs.eclipse.org/bugs/show_bug.cgi?id=167325
>>>>>
>>>>> I can not commit to any date because I'm not the one to decide whether
>>>>> my way of thinking is appropriate although I think I can convince
>>>>> Boris/Tod (JFace-Leads). But the more votes and comments the two bugs
>>>>> will get the better the solution will be the above bugs hold a dump of
>>>>> my brain how I could imagine this could work.
>>>>>
>>>>> If they follow me I will provide support in M5 but if this is not
>>>>> possible because of whatever reason there won't be support in 3.3
>>>>> because in M5 the API is frozen and I'll have no chance to get this
>>>>> new API in.
>>>>>
>>>>> By the way with M4 JFace will provide a widget independent
>>>>> AbstractTableViewer which Nebula components can subclass for their
>>>>> needs. Maybe the above bugs (151295, 167325) will modify the API
>>>>> slightly but that's not a big deal for implementors I think.
>>>>>
>>>>> Tom
>>>>>
>>>>> Al Major schrieb:
>>>>>> Tom Schindl wrote:
>>>>>>> [...]
>>>>>>>> * The ability to use controls at all times, instead of having to
>>>>>>>> click
>>>>>>>> the cell to bring up the editor.
>>>>>>> TableViewer/TreeViewer will hopefully also support this kind of
>>>>>>> feature
>>>>>>> in 3.3 timeframe (I'm working on it currently). Tabing support is
>>>>>> any timeframe on this as yet? is there a bug number that i can
>>>>>> track? i'd be happy to test any functionality you put out there. if
>>>>>> this is done comprehensively (there's a few life cycle events that
>>>>>> i've pointed out in discussions on CTableTree), it may be enough for
>>>>>> my current needs.
>>>>>>
>>>>>> thx,
>>>>>>
>>>>>> al
JFace for Nebula [was Re: Reactions to CompositeTable API] [message #20385 is a reply to message #20375] Tue, 12 December 2006 09:29 Go to previous messageGo to next message
Thomas Schindl is currently offline Thomas SchindlFriend
Messages: 5487
Registered: July 2009
Senior Member
Hi,

JFace will provide support for TreeViewer-Widget-Independency until M5
(because of API-Freeze this is not far away). I think the targeted
customers are Grid and CTableTree after M4 is out I'll start working on
it immediately and hope we can resolve this early in M5-timeframe
because there are other important areas I'd like to work on in JFace.

Tom

Al Major schrieb:
> i think Jeremy is still planning to re-use the updated JFace treeviewer
> as the basis for CTableTreeViewer. is that still correct, jeremy? if
> that's so, perhaps it would be best to introduce any changes into
> CTableTree and use that as the basis for changes to the base class in
> the 3.4 timeframe?
>
> regards,
>
> al
>
Re: Reactions to CompositeTable API [message #20404 is a reply to message #20375] Tue, 12 December 2006 14:17 Go to previous messageGo to next message
Jeremy Dowdall is currently offline Jeremy DowdallFriend
Messages: 181
Registered: July 2009
Senior Member
Al Major wrote:
> i think Jeremy is still planning to re-use the updated JFace treeviewer
> as the basis for CTableTreeViewer. is that still correct, jeremy?

That is correct
Re: Reactions to CompositeTable API [message #20411 is a reply to message #20364] Tue, 12 December 2006 14:42 Go to previous messageGo to next message
Jeremy Dowdall is currently offline Jeremy DowdallFriend
Messages: 181
Registered: July 2009
Senior Member
Al Major wrote:
> of the various options CTableTree does everything i need at the moment
> (ok so i have to hack it a bit to accomodate some life cycle events),
> except for one thing: support for ITreePathContentProvider. It was
> waiting on:
>
> https://bugs.eclipse.org/bugs/show_bug.cgi?id=154329
>
> but perhaps now it's waiting on
>
> https://bugs.eclipse.org/bugs/show_bug.cgi?id=167323
>
> jeremy can probably comment on this.

A widget independent AbstractTreeViewer will be a great help, and I am
definitely looking at using it for CTableTree.

> the only other weaknesses i have seen in CTableTree relative to other
> options.
> a) there were some display artifacts (flicker, bug in column redraw). i
> haven't gotten around to creating a simple test case that replicates
> these. this is just part of the maturing process (but the reason it
> makes sense to use something like the TableEditor solution which has
> already been used quite a bit).

Keep in mind that CTableTree is developed primarily on Linux GTK, so if
you're using CTableTree on windows - please log bugs, as I may not even
be seeing what you are :)
(and as an FYI: I now have a Mac development system so CTableTree,
CDateTime, and CKeypad will be working there soon)

> b) it would be nice to have control life cycle that only keeps controls
> around for the visible part of the tabletree (reuse these controls a la
> CompositeTable).

This and the viewer are top priorities for Q1 2007. I'm not planning on
being as virtual as CompositeTable, but there are certainly things that
can be done to improve resource consumption.
Re: Reactions to CompositeTable API [message #20430 is a reply to message #20316] Tue, 12 December 2006 15:50 Go to previous messageGo to next message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
Al Major wrote:
> David J. Orme wrote:
>>
>> 2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
>> items for *all* rows that have been displayed and then never destroys
>> them.
>>
>> In contrast, the row objects in CompositeTable correspond to exactly
>> the SWT controls that are visible. Once a row becomes invisible, it
>> ceases to exist as far as CompositeTable's layout is concerned. If
>> topRow() is 0, the visible table height is 20 rows, and
>> numRowsInCollection is 25, CompositeTable still only maintains row
>> objects for the top 20 rows. Not only that, but as soon as the user
>> scrolls forward one row, the top row control is immediately discarded,
>> a new one is created representing row 21, and all the controls in the
>> middle are shifted up. (In practice, CompositeTable recycles the row
>> objects, so there is no performance loss from creating and disposing
>> controls.)
>>
>> I could rename the "row" concept to "Item", but I'm concerned that
>> this would be confusing. They just are really different things, and
>> behave completely differently.
>>
>
> the recycling of controls is a great feature.
>
> is there a reasonable way to map a JFace style viewer (with items)
> onto CompositeTable rows? like Matthew, i quite like the specific style
> of MVC used by JFace.

This past weekend I committed code that will enable CompositeTable to
implement the TableViewer API.

The hard part is that cell editors just don't make sense with
CompositeTable since you can use whatever controls you want inside your
table.

> my use case requires GEF viewers embedded in table cells. all rows
> have the same height (which needs to be set). but there is a need to
> control the order in which viewers in different columns of the same row
> are initialized.

Hmmmm... The JFace approach seems to require that the control in the
row be fixed. There is no support in TableViewer for anything other
than a Label or Text-like thing in the table cell itself.

Maybe we could work on the API together and come up with something
reasonable?


Regards,

Dave Orme
Re: Reactions to CompositeTable API [message #21112 is a reply to message #20430] Fri, 15 December 2006 11:29 Go to previous messageGo to next message
Eclipse UserFriend
Originally posted by: alnospammajor.noboxspamspoon.com

David J. Orme wrote:
>>
>> the recycling of controls is a great feature.
>>
>> is there a reasonable way to map a JFace style viewer (with items)
>> onto CompositeTable rows? like Matthew, i quite like the specific
>> style of MVC used by JFace.
>
> This past weekend I committed code that will enable CompositeTable to
> implement the TableViewer API.
>
> The hard part is that cell editors just don't make sense with
> CompositeTable since you can use whatever controls you want inside your
> table.
>
not entirely sure i understand. if you're saying that you allow
arbitrary controls on the grid cells, that's the feature i would really
like to see. doesn't have to be implemented with the Cell Editors.
whatever turns out to make the most sense for CTableTree/CompositeTable
should be refactored back into JFace if so desired.

>> my use case requires GEF viewers embedded in table cells. all rows
>> have the same height (which needs to be set). but there is a need to
>> control the order in which viewers in different columns of the same
>> row are initialized.
>
> Hmmmm... The JFace approach seems to require that the control in the
> row be fixed. There is no support in TableViewer for anything other
> than a Label or Text-like thing in the table cell itself.
>
this support does not currently exist, but if there's some clean way to
include it, perhaps the JFace folks can be convinced to do so?

> Maybe we could work on the API together and come up with something
> reasonable?
>

i'd be happy to pitch in ideas. unfortunately i haven't really explored
the CompositeTable code, so i can't say anything very intelligent about
it at the moment. in part this is because all my own stuff uses viewers,
making the apparent initial investment in CompositeTable larger than i'd
like.

regards,

al
Re: Reactions to CompositeTable API [message #21160 is a reply to message #21112] Fri, 15 December 2006 14:30 Go to previous messageGo to next message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
Al Major wrote:
> David J. Orme wrote:
>>>
>>> the recycling of controls is a great feature.
>>>
>>> is there a reasonable way to map a JFace style viewer (with
>>> items) onto CompositeTable rows? like Matthew, i quite like the
>>> specific style of MVC used by JFace.
>>
>> This past weekend I committed code that will enable CompositeTable to
>> implement the TableViewer API.
>>
>> The hard part is that cell editors just don't make sense with
>> CompositeTable since you can use whatever controls you want inside
>> your table.
>>
> not entirely sure i understand. if you're saying that you allow
> arbitrary controls on the grid cells, that's the feature i would really
> like to see. doesn't have to be implemented with the Cell Editors.

Yes, that's the whole point of CompositeTable

> whatever turns out to make the most sense for CTableTree/CompositeTable
> should be refactored back into JFace if so desired.

Maybe. There are really two use-cases for CompositeTable:

1) The standard table is too slow and you have all this code that
depends on JFace TableViewers. You're only using the TableViewer to
display, not to edit data. In this situation, CompositeTable could be a
drop-in replacement that can improve performance quite a bit.

2) If you need to use any control inside a "cell". Actually
CompositeTable's notion of a "cell" is just the set of controls that are
in the row object's tab list. They don't have to be arranged in any
particular way in the UI.

>>> my use case requires GEF viewers embedded in table cells. all
>>> rows have the same height (which needs to be set). but there is a
>>> need to control the order in which viewers in different columns of
>>> the same row are initialized.
>>
>> Hmmmm... The JFace approach seems to require that the control in the
>> row be fixed. There is no support in TableViewer for anything other
>> than a Label or Text-like thing in the table cell itself.
>>
> this support does not currently exist, but if there's some clean way
> to include it, perhaps the JFace folks can be convinced to do so?

Maybe. I want to take a look at that problem and see.

>> Maybe we could work on the API together and come up with something
>> reasonable?
>>
> i'd be happy to pitch in ideas. unfortunately i haven't really
> explored the CompositeTable code, so i can't say anything very
> intelligent about it at the moment. in part this is because all my own
> stuff uses viewers, making the apparent initial investment in
> CompositeTable larger than i'd like.

Although CompositeTable isn't a viewer, its API is structured in a
similar way to JFace viewers, so the conversion might not be as bad as
you would think.


Regards,

Dave Orme
Re: Reactions to CompositeTable API [message #21207 is a reply to message #21160] Sun, 17 December 2006 03:34 Go to previous messageGo to next message
Eclipse UserFriend
Originally posted by: alnospammajor.noboxspamspoon.com

David J. Orme wrote:
>> i'd be happy to pitch in ideas. unfortunately i haven't really
>> explored the CompositeTable code, so i can't say anything very
>> intelligent about it at the moment. in part this is because all my own
>> stuff uses viewers, making the apparent initial investment in
>> CompositeTable larger than i'd like.
>
> Although CompositeTable isn't a viewer, its API is structured in a
> similar way to JFace viewers, so the conversion might not be as bad as
> you would think.
>

i'll try to look at it the next time i'm actively working on the grid
related stuff. i do need tree functionality in certain parts of my code,
so overall CTableTree is a better fit. but it would be nice if the
common functionality of all these projects was available as a uniform
(preferably JFace) API (i do recognize that may not be a priority for
the folks that are responsible for the components, so may not happen
soon/ever :-)

regards,

al
Re: Reactions to CompositeTable API [message #21223 is a reply to message #21207] Sun, 17 December 2006 03:45 Go to previous messageGo to next message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
Al Major wrote:
> David J. Orme wrote:
>> Although CompositeTable isn't a viewer, its API is structured in a
>> similar way to JFace viewers, so the conversion might not be as bad as
>> you would think.
>
> i'll try to look at it the next time i'm actively working on the
> grid related stuff. i do need tree functionality in certain parts of my
> code, so overall CTableTree is a better fit. but it would be nice if the
> common functionality of all these projects was available as a uniform
> (preferably JFace) API (i do recognize that may not be a priority for
> the folks that are responsible for the components, so may not happen
> soon/ever :-)

It's a tough decision:

- Supporting the JFace API would make it easier for folks to adopt
CompositeTable.

- On the other hand, the JFace ContentProvider isn't lazy, so you would
lose significant performance and scalability compared with the current
CompositeTable API.

At the end of the day, I'll probably provide a JFace wrapper for
CompositeTable, and document the drawbacks of using that API.


Regards,

Dave Orme

--
Senior Consultant, Trainer
Coconut Palm Software, Inc.
http://www.coconut-palm-software.com
Re: Reactions to CompositeTable API [message #21239 is a reply to message #20411] Mon, 18 December 2006 13:33 Go to previous messageGo to next message
Eclipse UserFriend
Originally posted by: alnospammajor.noboxspamspoon.com

Jeremy Dowdall wrote:
>
>> the only other weaknesses i have seen in CTableTree relative to other
>> options.
>> a) there were some display artifacts (flicker, bug in column redraw).
>> i haven't gotten around to creating a simple test case that replicates
>> these. this is just part of the maturing process (but the reason it
>> makes sense to use something like the TableEditor solution which has
>> already been used quite a bit).
>
> Keep in mind that CTableTree is developed primarily on Linux GTK, so if
> you're using CTableTree on windows - please log bugs, as I may not even
> be seeing what you are :)
> (and as an FYI: I now have a Mac development system so CTableTree,
> CDateTime, and CKeypad will be working there soon)
>

next time i see something, i'll try to replicate it using one of your
snippets as a base example (if i can :-). that'll make it easier to
report bugs in a more useful form.

thx,

al
Re: Reactions to CompositeTable API [message #24839 is a reply to message #21239] Sun, 28 January 2007 19:27 Go to previous messageGo to next message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
Thanks!


Dave

Al Major wrote:
> Jeremy Dowdall wrote:
>>
>>> the only other weaknesses i have seen in CTableTree relative to other
>>> options.
>>> a) there were some display artifacts (flicker, bug in column redraw).
>>> i haven't gotten around to creating a simple test case that
>>> replicates these. this is just part of the maturing process (but the
>>> reason it makes sense to use something like the TableEditor solution
>>> which has already been used quite a bit).
>>
>> Keep in mind that CTableTree is developed primarily on Linux GTK, so
>> if you're using CTableTree on windows - please log bugs, as I may not
>> even be seeing what you are :)
>> (and as an FYI: I now have a Mac development system so CTableTree,
>> CDateTime, and CKeypad will be working there soon)
>>
>
> next time i see something, i'll try to replicate it using one of
> your snippets as a base example (if i can :-). that'll make it easier to
> report bugs in a more useful form.
>
> thx,
>
> al
>


--
Senior Consultant, Trainer
Coconut Palm Software, Inc.
http://www.coconut-palm-software.com
Re: Reactions to CompositeTable API [message #42800 is a reply to message #24839] Sat, 03 November 2007 16:01 Go to previous message
AJ Bencomo is currently offline AJ BencomoFriend
Messages: 42
Registered: July 2009
Member
Hi David,

Is a possible to create a CompositeTable with more than 2 columns?

Thanks,
-AJ
Re: Reactions to CompositeTable API [message #570445 is a reply to message #18076] Thu, 30 November 2006 18:13 Go to previous message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
Matthew Hall wrote:
> I've been looking over the API for CompositeTable and wanted to share
> some of my reactions for discussion.

Thanks for your thoughtful comments!

> First of all, this control is a great idea and as evidenced by the
> response on the newsgroups, is useful for a fair number of people,
> including myself.

Thanks!

> However the stated goal of Nebula is to be a proving
> ground for custom widgets, with the eventual goal of those widgets being
> adopted into SWT proper. I think that the CompositeTable API deviates
> from SWT conventions to such a degree that will make its adoption into
> SWT unlikely. Thus I would like to see CompositeTable refactored to
> makes its API more like the rest of SWT.

To the extent that this is possible, I'd like to see this too.

> For example: Table, Tree and TabFolder expose their content through
> TableItem, TreeItem and TabItem and developers are used to interacting
> with them. By contrast, CompositeTable uses prototyping to define rows
> and possibly headers. This is a very unfamiliar approach in Java, let
> alone in SWT. I think everyone would be more comfortable with a
> CompositeItem concept rather than this nebulous (forgive the pun)
> prototyping scheme.

Can you explain what you mean by a CompositeItem object? I'm a bit
confused.

The reason I'm confused is that CompositeTable really has *no* concept
that is similar to the *Item concept in the standard controls.

For example:

1) The *Item concept in SWT mainly represents what *data* will be placed
in the specified columns, along with some layout information (width, etc).

2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
items for *all* rows that have been displayed and then never destroys them.

In contrast, the row objects in CompositeTable correspond to exactly the
SWT controls that are visible. Once a row becomes invisible, it ceases
to exist as far as CompositeTable's layout is concerned. If topRow() is
0, the visible table height is 20 rows, and numRowsInCollection is 25,
CompositeTable still only maintains row objects for the top 20 rows.
Not only that, but as soon as the user scrolls forward one row, the top
row control is immediately discarded, a new one is created representing
row 21, and all the controls in the middle are shifted up. (In
practice, CompositeTable recycles the row objects, so there is no
performance loss from creating and disposing controls.)

I could rename the "row" concept to "Item", but I'm concerned that this
would be confusing. They just are really different things, and behave
completely differently.

Did I correctly understand your suggestion?

> On the same note, the Table and Tree widgets have a method setItemCount
> to set the number of items, whereas in CompositeTable this is called
> setNumRowsInCollection.

If I called it setItemCount, this would imply that if you
setItemCount(1000000), that there would be a million CompositeTableItem
objects somewhere, which simply isn't true.

> I don't like the design-mode / active-mode paradigm.

Neither do I.

There are two reasons this exists: One major goal I had when creating
CompositeTable is that it would be simple to use within Visual Editor.

I could use Beans.isDesignTime() in the control and maybe I should do
that, but I wanted the control behave inside VE exactly the way it
behaves at run-time. This way you can more easily learn to use the
control by changing the properties interactively in VE and watching what
happens.

The only way to accomplish this is to have a property that explicitly
switches the control from design-time behavior to run-time behavior.

The second reason is that JavaBeans isn't in Foundation profile. So in
order to support Foundation, I can't use Beans.isDesignTime().

But maybe this property was a bad idea.

I'd be happy for feedback on this. What do folks think?

> Then there is the use of reflection. Although I recognize that Dave
> Orme (who authored the control) would be quite comfortable with
> reflection, given his role in VE and data binding, I am nonetheless
> uncomfortable with it. Using reflection is a performance hit, is
> brittle, and really isn't necessary if we just invent an interface to
> replace it (ICompositeRowBuilder). Moreover it makes adoption into SWT
> impossible since (as I understand it) reflection is not available in the
> CDC-1.0/Foundation-1.0 runtime environment.

There is a really good question here, but a few misconceptions too.
I'll clear away the misconceptions first, and then we can hopefully
tackle the underlying question more productively:

1) On Foundation support: reflection is there but not dynamic proxies or
JavaBean support.

2) Regarding performance, reflection is only used to construct new row
controls. But once a row control is constructed, it is never destroyed
until the entire CompositeTable control is destroyed. (Instead,
CompositeTable recycles row objects.) So if your table has 20 rows of
data in it, there will be exactly 20 reflection calls the first time
your data is displayed and no more reflection calls after that. Since
reflection is never used any more after the row controls are
constructed, performance just isn't an issue here.

(CompositeTable never creates more row objects than can be displayed in
the window at once, so the upper bound of row controls created is
exactly the same number as the number of controls you would have if you
created the same layout by hand.)

3) I don't understand how reflection is brittle in this case?

Now on to the underlying question (the whole reason I use reflection to
begin with):

> And I REALLY don't like being forced to extend composite for my rows,
> when we could just define an interface that creates and manages a
> composite instead. This is a very Swing way of using SWT.

As stated above, a design goal for CompositeTable was to be able to edit
the table visually using Visual Editor. Visual Editor knows how to edit
a custom Composite, but not how to edit a JFace-like createControl() UI
factory.

However, I would like to be able to accommodate folks that would prefer
to use an interface. If someone can propose an API that makes sense and
doesn't lose the VE support, I'd be very glad to listen.

> It would also seem more appropriate to use SWT.SetData listeners like
> the other virtual controls instead of addRowContentProvider.

Again, it's a possibility to try to mimic the SWT names, but don't you
feel that folks will be confused here? In CompositeTable's event, one
normally doesn't set data into some *Item object, but rather sets data
into real SWT controls in your row object or possibly uses data binding
to bind those controls to a domain model object.

What CompositeTable does here seems closer conceptually to the JFace
content provider concept, which is why this name was chosen.

I'm willing to rename this, but I'm concerned about confusion.

> Just my $0.02. What does everybody else think?

Thanks for your feedback!

In balance, CompositeTable tries to reflect and synthesize ideas from
all of SWT + JFace + Visual Editor + Eclipse Data binding APIs. My hope
is that this will make folks more productive and result in more
maintainable applications.

Thanks for trying to help make it better.

> (Should this be posted in Bugzilla instead?)
>
> Thanks for listening

I think that the newsgroup is the best place for this discussion right
now. If specific feature requests come out of this discussion, those
should go into Bugzilla.

Thanks for writing. :)


Best regards,

Dave Orme
Re: Reactions to CompositeTable API [message #570604 is a reply to message #18758] Thu, 30 November 2006 22:34 Go to previous message
Matthew Hall is currently offline Matthew HallFriend
Messages: 368
Registered: July 2009
Senior Member
A snippet's worth a thousand words:


CompositeTable table = new CompositeTable(parent, SWT.VIRTUAL | SWT.BORDER);

// I like the class as a manager for the row, I just don't think it
// should extend Composite by design
// Adding this interface will remove all that reflection code
interface ICompositeRow {
   // Implementers are responsible for making getControl() return the
   // created control
   void createControl(CompositeTable table);
   Control getControl();
}

abstract class CompositeRow implements ICompositeRow {
   Control control;

   Control getControl() {
     return control;
   }

   /** Sets the control returned by getControl */
   void setControl(Control control) {
     this.control = control;
   }
}

class MyHeader extends CompositeRow {
   Label first;
   Label last;

   void createControl(CompositeTable table) {
     Composite composite = new Composite(table, SWT.NONE);
     first = new Label(composite, SWT.NONE);
     last = new Label(composite, SWT.NONE);
     first.setText("First");
     last.setText("Last");
     setControl(composite);
   }
}

table.setHeaderProvider(new IRowProvider() {
   ICompositeRow createRow() { return new MyHeader(); }
});

class MyRow implements ICompositeRow {
   Text first;
   Text last;

   void createControl(CompositeTable table) {
     Composite composite = new Composite(table, SWT.NONE);
     first = new Text(composite, SWT.BORDER);
     last = new Text(composite, SWT.BORDER);
     setControl(composite);
   }
}

table.setRowProvider(new IRowProvider() {
   ICompositeRow createRow() { return new MyRow(); }
});

// The CompositeItem is basically the JFace wrapper around the content
abstract class CompositeItem extends Item {
   CompositeItem(CompositeTable table, int style) {
     super(table, style);
     table.addItem(this);
   }

   CompositeItem(CompositeTable table, int style, int index) {
     super(table, style);
     table.addItem(this, index);
   }

   // This property is managed by CompositeTable as it scrolls up
   // and down
   ICompositeRow row = null;
   ICompositeRow getRow() { return row; }
   void setRow(ICompositeRow row) {
     if (this.row != null)
       unhookListeners(this.row);

     this.row = row;
     updateRow();

     if (row != null)
       hookListeners(row);
   }

   // These methods may be over-designed, but just a thought
   // off the top of my head
   // DataBinding would really help here
   abstract void hookListeners(ICompositeRow row);
   abstract void unhookListeners(ICompositeRow row);
   abstract void updateRow();
}

class MyItem extends CompositeItem implements Listener {
   Name name = null;

   MyItem(CompositeTable table, int style) {
     super(table, style);
   }

   MyItem(CompositeTable table, int style, int index, Name name) {
     super(table, style, index);
   }

   Name getName() { return name; }
   void setName(Name name) {
     this.name = name;
     updateRow();
   }

   void hookListeners(ICompositeRow row) {
     MyRow r = (MyRow) row;
     r.first.addListener(SWT.Modify, this);
     r.last.addListener(SWT.Modify, this);
   }

   void unhookListeners(ICompositeRow row) {
     MyRow r = (MyRow) row;
     r.first.removeListener(SWT.Modify, this);
     r.last.removeListener(SWT.Modify, this);
   }

   void updateRow() {
     MyRow r = (MyRow) getRow();
     if (r == null) return;
     r.first.setText(name == null ? "" : name.getFirst());
     r.last.setText(name == null ? "" : name.getLast());
   }

   void handleEvent(Event e) {
     if (name == null) return;

     MyRow row = (MyRow) getRow();
     if (e.widget == row.first)
       name.setFirst(row.first.getText());
     else if (e.widget == row.last)
       name.setLast(row.last.getText());
   }
}

table.setItemProvider(new ICompositeItemProvider() {
   CompositeItem createItem(CompositeTable table, int style, int index) {
     return new MyItem(table, style, index);
   }
});

table.addListener(SWT.SetData, new Listener() {
   void handleEvent(Event e) {
     MyItem item = (MyItem) e.item;
     int index = table.indexOf(item);
     item.setName(Names.get(index));
   }
});

table.setItemCount(Names.getCount());



This is just a rough sketch of what I had in mind.

> 1) The *Item concept in SWT mainly represents what *data* will be placed
> in the specified columns, along with some layout information (width, etc).
>
> 2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
> items for *all* rows that have been displayed and then never destroys them.

As outlined above, an Item is a separate concept from a Row. The item
maps to the data, where the Row maps to the visible display.

> If I called it setItemCount, this would imply that if you
> setItemCount(1000000), that there would be a million CompositeTableItem
> objects somewhere, which simply isn't true.

Not necessarily. This behavior could be emulated and items created on
the fly as they are needed for display by the ICompositeItemProvider,
and initialized by the SWT.SetData listener.

It would also be useful to have SWT.VIRTUAL be an option instead of a
given. This would allow users to just instantiate their items as needed
for small collections, which would result in simpler code:

for (int i = 0; i < Names.getCount(); i++)
   new MyItem(table, SWT.NONE).setName(Names.get(i));


>> I don't like the design-mode / active-mode paradigm.
>
> Neither do I.
>
> There are two reasons this exists: One major goal I had when creating
> CompositeTable is that it would be simple to use within Visual Editor.
>
> I could use Beans.isDesignTime() in the control and maybe I should do
> that, but I wanted the control behave inside VE exactly the way it
> behaves at run-time. This way you can more easily learn to use the
> control by changing the properties interactively in VE and watching what
> happens.
>
> The only way to accomplish this is to have a property that explicitly
> switches the control from design-time behavior to run-time behavior.
>
> The second reason is that JavaBeans isn't in Foundation profile. So in
> order to support Foundation, I can't use Beans.isDesignTime().
>
> But maybe this property was a bad idea.
>
> I'd be happy for feedback on this. What do folks think?
>

Perhaps make the property false by default? The design changes I'm
suggesting would not prevent this option, but it is a little jarring to
have this setDesignTime(false) method call in the middle of my code.

>> Then there is the use of reflection. Although I recognize that Dave
>> Orme (who authored the control) would be quite comfortable with
>> reflection, given his role in VE and data binding, I am nonetheless
>> uncomfortable with it. Using reflection is a performance hit, is
>> brittle, and really isn't necessary if we just invent an interface to
>> replace it (ICompositeRowBuilder). Moreover it makes adoption into
>> SWT impossible since (as I understand it) reflection is not available
>> in the CDC-1.0/Foundation-1.0 runtime environment.
>
> There is a really good question here, but a few misconceptions too. I'll
> clear away the misconceptions first, and then we can hopefully tackle
> the underlying question more productively:
>
> 1) On Foundation support: reflection is there but not dynamic proxies or
> JavaBean support.

Good to know

>
> 2) Regarding performance, reflection is only used to construct new row
> controls. But once a row control is constructed, it is never destroyed
> until the entire CompositeTable control is destroyed. (Instead,
> CompositeTable recycles row objects.) So if your table has 20 rows of
> data in it, there will be exactly 20 reflection calls the first time
> your data is displayed and no more reflection calls after that. Since
> reflection is never used any more after the row controls are
> constructed, performance just isn't an issue here.

True, but a regular old java interface like IRowProvider is much more
comfortable to Java programmers than duck typing.

> 3) I don't understand how reflection is brittle in this case?

It excludes the possibility of other constructor signatures, such as
MyCompositeRow(CompositeTable table) where the style bit is implicit.
Although considered bad form in SWT, this is a legitimate choice for the
developer.

> Now on to the underlying question (the whole reason I use reflection to
> begin with):
>
>> And I REALLY don't like being forced to extend composite for my rows,
>> when we could just define an interface that creates and manages a
>> composite instead. This is a very Swing way of using SWT.
>
> As stated above, a design goal for CompositeTable was to be able to edit
> the table visually using Visual Editor. Visual Editor knows how to edit
> a custom Composite, but not how to edit a JFace-like createControl() UI
> factory.

The JFace createControl() factory paradigm is pervasive throughout the
platform. I think the "knows how to edit" use case really belongs in
VE, not in each control we hope to use in VE.

> However, I would like to be able to accommodate folks that would prefer
> to use an interface. If someone can propose an API that makes sense and
> doesn't lose the VE support, I'd be very glad to listen.

Perhaps you could point me to some HOWTO's or tutorials for teaching VE
how to design custom controls, and I'll help you work on it.

>> It would also seem more appropriate to use SWT.SetData listeners like
>> the other virtual controls instead of addRowContentProvider.
>
> Again, it's a possibility to try to mimic the SWT names, but don't you
> feel that folks will be confused here?

That's a question for the bystanders!

Maybe it would help if we following Steve Northover's advice and set the
SWT.SMART bit on the CompositeTable. :)

> In CompositeTable's event, one
> normally doesn't set data into some *Item object, but rather sets data
> into real SWT controls in your row object or possibly uses data binding
> to bind those controls to a domain model object.

Sorry, I should have explained that in my original post. In my proposed
design the concrete CompositeItem subclass is responsible for populating
the ICompositeRow fields and managing the binding between those
controls. This is a departure from SWT conventions, but as you say this
is a different beast, and I felt it was the least "weird" of approaches.
Your mileage my vary.

> What CompositeTable does here seems closer conceptually to the JFace
> content provider concept, which is why this name was chosen.
>
> I'm willing to rename this, but I'm concerned about confusion.

To me this design feels a lot clearer and simpler, but I acknowledge
that this may be confusing to others.

> In balance, CompositeTable tries to reflect and synthesize ideas from
> all of SWT + JFace + Visual Editor + Eclipse Data binding APIs. My hope
> is that this will make folks more productive and result in more
> maintainable applications.

Thanks Dave for taking the time to respond.

Matthew
Re: Reactions to CompositeTable API [message #570784 is a reply to message #18825] Fri, 01 December 2006 14:34 Go to previous message
Chris Gross is currently offline Chris GrossFriend
Messages: 471
Registered: July 2009
Senior Member
Hi Matthew,

Can I ask a (perhaps dumb) question? You seem to want to change alot of
the CompositeTable API and make it fit in better with SWT, etc. With
all these changes wouldn't the end result be much like a regular SWT
Table that is populated with widgets using TableEditors (except that the
editors are only created on visible rows)? In other words, it sounds
like alot of what you don't like is what makes CompositeTable unique.
What is the feature (or features) from CompositeTable that you think are
the killer (i.e. killer in a good way ;)?

Regards,
-Chris

Matthew Hall wrote:
> A snippet's worth a thousand words:
>
>
> 
> CompositeTable table = new CompositeTable(parent, SWT.VIRTUAL | 
> SWT.BORDER);
> 
> // I like the class as a manager for the row, I just don't think it
> // should extend Composite by design
> // Adding this interface will remove all that reflection code
> interface ICompositeRow {
>   // Implementers are responsible for making getControl() return the
>   // created control
>   void createControl(CompositeTable table);
>   Control getControl();
> }
> 
> abstract class CompositeRow implements ICompositeRow {
>   Control control;
> 
>   Control getControl() {
>     return control;
>   }
> 
>   /** Sets the control returned by getControl */
>   void setControl(Control control) {
>     this.control = control;
>   }
> }
> 
> class MyHeader extends CompositeRow {
>   Label first;
>   Label last;
> 
>   void createControl(CompositeTable table) {
>     Composite composite = new Composite(table, SWT.NONE);
>     first = new Label(composite, SWT.NONE);
>     last = new Label(composite, SWT.NONE);
>     first.setText("First");
>     last.setText("Last");
>     setControl(composite);
>   }
> }
> 
> table.setHeaderProvider(new IRowProvider() {
>   ICompositeRow createRow() { return new MyHeader(); }
> });
> 
> class MyRow implements ICompositeRow {
>   Text first;
>   Text last;
> 
>   void createControl(CompositeTable table) {
>     Composite composite = new Composite(table, SWT.NONE);
>     first = new Text(composite, SWT.BORDER);
>     last = new Text(composite, SWT.BORDER);
>     setControl(composite);
>   }
> }
> 
> table.setRowProvider(new IRowProvider() {
>   ICompositeRow createRow() { return new MyRow(); }
> });
> 
> // The CompositeItem is basically the JFace wrapper around the content
> abstract class CompositeItem extends Item {
>   CompositeItem(CompositeTable table, int style) {
>     super(table, style);
>     table.addItem(this);
>   }
> 
>   CompositeItem(CompositeTable table, int style, int index) {
>     super(table, style);
>     table.addItem(this, index);
>   }
> 
>   // This property is managed by CompositeTable as it scrolls up
>   // and down
>   ICompositeRow row = null;
>   ICompositeRow getRow() { return row; }
>   void setRow(ICompositeRow row) {
>     if (this.row != null)
>       unhookListeners(this.row);
> 
>     this.row = row;
>     updateRow();
> 
>     if (row != null)
>       hookListeners(row);
>   }
> 
>   // These methods may be over-designed, but just a thought
>   // off the top of my head
>   // DataBinding would really help here
>   abstract void hookListeners(ICompositeRow row);
>   abstract void unhookListeners(ICompositeRow row);
>   abstract void updateRow();
> }
> 
> class MyItem extends CompositeItem implements Listener {
>   Name name = null;
> 
>   MyItem(CompositeTable table, int style) {
>     super(table, style);
>   }
> 
>   MyItem(CompositeTable table, int style, int index, Name name) {
>     super(table, style, index);
>   }
> 
>   Name getName() { return name; }
>   void setName(Name name) {
>     this.name = name;
>     updateRow();
>   }
> 
>   void hookListeners(ICompositeRow row) {
>     MyRow r = (MyRow) row;
>     r.first.addListener(SWT.Modify, this);
>     r.last.addListener(SWT.Modify, this);
>   }
> 
>   void unhookListeners(ICompositeRow row) {
>     MyRow r = (MyRow) row;
>     r.first.removeListener(SWT.Modify, this);
>     r.last.removeListener(SWT.Modify, this);
>   }
> 
>   void updateRow() {
>     MyRow r = (MyRow) getRow();
>     if (r == null) return;
>     r.first.setText(name == null ? "" : name.getFirst());
>     r.last.setText(name == null ? "" : name.getLast());
>   }
> 
>   void handleEvent(Event e) {
>     if (name == null) return;
> 
>     MyRow row = (MyRow) getRow();
>     if (e.widget == row.first)
>       name.setFirst(row.first.getText());
>     else if (e.widget == row.last)
>       name.setLast(row.last.getText());
>   }
> }
> 
> table.setItemProvider(new ICompositeItemProvider() {
>   CompositeItem createItem(CompositeTable table, int style, int index) {
>     return new MyItem(table, style, index);
>   }
> });
> 
> table.addListener(SWT.SetData, new Listener() {
>   void handleEvent(Event e) {
>     MyItem item = (MyItem) e.item;
>     int index = table.indexOf(item);
>     item.setName(Names.get(index));
>   }
> });
> 
> table.setItemCount(Names.getCount());
> 
> 

>
> This is just a rough sketch of what I had in mind.
>
>> 1) The *Item concept in SWT mainly represents what *data* will be
>> placed in the specified columns, along with some layout information
>> (width, etc).
>>
>> 2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
>> items for *all* rows that have been displayed and then never destroys
>> them.
>
> As outlined above, an Item is a separate concept from a Row. The item
> maps to the data, where the Row maps to the visible display.
>
>> If I called it setItemCount, this would imply that if you
>> setItemCount(1000000), that there would be a million
>> CompositeTableItem objects somewhere, which simply isn't true.
>
> Not necessarily. This behavior could be emulated and items created on
> the fly as they are needed for display by the ICompositeItemProvider,
> and initialized by the SWT.SetData listener.
>
> It would also be useful to have SWT.VIRTUAL be an option instead of a
> given. This would allow users to just instantiate their items as needed
> for small collections, which would result in simpler code:
>
>
> for (int i = 0; i < Names.getCount(); i++)
>   new MyItem(table, SWT.NONE).setName(Names.get(i));
> 

>
>>> I don't like the design-mode / active-mode paradigm.
>>
>> Neither do I.
>>
>> There are two reasons this exists: One major goal I had when creating
>> CompositeTable is that it would be simple to use within Visual Editor.
>>
>> I could use Beans.isDesignTime() in the control and maybe I should do
>> that, but I wanted the control behave inside VE exactly the way it
>> behaves at run-time. This way you can more easily learn to use the
>> control by changing the properties interactively in VE and watching
>> what happens.
>>
>> The only way to accomplish this is to have a property that explicitly
>> switches the control from design-time behavior to run-time behavior.
>>
>> The second reason is that JavaBeans isn't in Foundation profile. So
>> in order to support Foundation, I can't use Beans.isDesignTime().
>>
>> But maybe this property was a bad idea.
>>
>> I'd be happy for feedback on this. What do folks think?
>>
>
> Perhaps make the property false by default? The design changes I'm
> suggesting would not prevent this option, but it is a little jarring to
> have this setDesignTime(false) method call in the middle of my code.
>
>>> Then there is the use of reflection. Although I recognize that Dave
>>> Orme (who authored the control) would be quite comfortable with
>>> reflection, given his role in VE and data binding, I am nonetheless
>>> uncomfortable with it. Using reflection is a performance hit, is
>>> brittle, and really isn't necessary if we just invent an interface to
>>> replace it (ICompositeRowBuilder). Moreover it makes adoption into
>>> SWT impossible since (as I understand it) reflection is not available
>>> in the CDC-1.0/Foundation-1.0 runtime environment.
>>
>> There is a really good question here, but a few misconceptions too.
>> I'll clear away the misconceptions first, and then we can hopefully
>> tackle the underlying question more productively:
>>
>> 1) On Foundation support: reflection is there but not dynamic proxies
>> or JavaBean support.
>
> Good to know
>
>>
>> 2) Regarding performance, reflection is only used to construct new row
>> controls. But once a row control is constructed, it is never
>> destroyed until the entire CompositeTable control is destroyed.
>> (Instead, CompositeTable recycles row objects.) So if your table has
>> 20 rows of data in it, there will be exactly 20 reflection calls the
>> first time your data is displayed and no more reflection calls after
>> that. Since reflection is never used any more after the row controls
>> are constructed, performance just isn't an issue here.
>
> True, but a regular old java interface like IRowProvider is much more
> comfortable to Java programmers than duck typing.
>
>> 3) I don't understand how reflection is brittle in this case?
>
> It excludes the possibility of other constructor signatures, such as
> MyCompositeRow(CompositeTable table) where the style bit is implicit.
> Although considered bad form in SWT, this is a legitimate choice for the
> developer.
>
>> Now on to the underlying question (the whole reason I use reflection
>> to begin with):
>>
>>> And I REALLY don't like being forced to extend composite for my rows,
>>> when we could just define an interface that creates and manages a
>>> composite instead. This is a very Swing way of using SWT.
>>
>> As stated above, a design goal for CompositeTable was to be able to
>> edit the table visually using Visual Editor. Visual Editor knows how
>> to edit a custom Composite, but not how to edit a JFace-like
>> createControl() UI factory.
>
> The JFace createControl() factory paradigm is pervasive throughout the
> platform. I think the "knows how to edit" use case really belongs in
> VE, not in each control we hope to use in VE.
>
>> However, I would like to be able to accommodate folks that would
>> prefer to use an interface. If someone can propose an API that makes
>> sense and doesn't lose the VE support, I'd be very glad to listen.
>
> Perhaps you could point me to some HOWTO's or tutorials for teaching VE
> how to design custom controls, and I'll help you work on it.
>
>>> It would also seem more appropriate to use SWT.SetData listeners like
>>> the other virtual controls instead of addRowContentProvider.
>>
>> Again, it's a possibility to try to mimic the SWT names, but don't you
>> feel that folks will be confused here?
>
> That's a question for the bystanders!
>
> Maybe it would help if we following Steve Northover's advice and set the
> SWT.SMART bit on the CompositeTable. :)
>
>> In CompositeTable's event, one normally doesn't set data into some
>> *Item object, but rather sets data into real SWT controls in your row
>> object or possibly uses data binding to bind those controls to a
>> domain model object.
>
> Sorry, I should have explained that in my original post. In my proposed
> design the concrete CompositeItem subclass is responsible for populating
> the ICompositeRow fields and managing the binding between those
> controls. This is a departure from SWT conventions, but as you say this
> is a different beast, and I felt it was the least "weird" of approaches.
> Your mileage my vary.
>
>> What CompositeTable does here seems closer conceptually to the JFace
>> content provider concept, which is why this name was chosen.
>>
>> I'm willing to rename this, but I'm concerned about confusion.
>
> To me this design feels a lot clearer and simpler, but I acknowledge
> that this may be confusing to others.
>
>> In balance, CompositeTable tries to reflect and synthesize ideas from
>> all of SWT + JFace + Visual Editor + Eclipse Data binding APIs. My
>> hope is that this will make folks more productive and result in more
>> maintainable applications.
>
> Thanks Dave for taking the time to respond.
>
> Matthew
Re: Reactions to CompositeTable API [message #570892 is a reply to message #18916] Fri, 01 December 2006 17:22 Go to previous message
Matthew Hall is currently offline Matthew HallFriend
Messages: 368
Registered: July 2009
Senior Member
Chris Gross wrote:
> Can I ask a (perhaps dumb) question? You seem to want to change a lot of
> the CompositeTable API and make it fit in better with SWT, etc.

I'm not trying to rock the boat here. David Orme himself said that he
want to avoid confusing users. I'm making these suggestions because I
think it will make the control simpler and more intuitive. And I'm not
suggesting that my ideas are the best--I'm trying to get a dialog going.

> With all these changes wouldn't the end result be much like a regular SWT
> Table that is populated with widgets using TableEditors (except that the
> editors are only created on visible rows)? In other words, it sounds
> like alot of what you don't like is what makes CompositeTable unique.

Not really. I'm suggesting changes to the API to make what
CompositeTable does more accessible to SWT programmers. The
reservations I have are:

* I dislike reflection because however you use reflection becomes de
facto API, except the compiler can't check for bad usage. Who knows if
somebody will refactor your Row class down the road, not knowing it
*has* to have a (Composite, int) constructor? The compiler will *never*
catch this. A documented interface instead of reflection will avoid
this problem. Besides, it may be possible to just have the default
IRowProvider perform this exact behavior so that current CompositeTable
users can just keep doing prototyping if they prefer.
* SWT programmers are used to working with *Items. Working with items
the non-virtual way is much easier than the virtual way, and I would
like an option between the two.
* Renaming some of the API (numRowsInCollection == itemCount) to match
SWT naming conventions will make using this control more intuitive.

> What is the feature (or features) from CompositeTable that you think are
> the killer (i.e. killer in a good way ;)?

* The ability to use controls at all times, instead of having to click
the cell to bring up the editor.
* The ability to lay out those controls any way you like within the row
if the standard left-to-right columnar layout doesn't suit you.

I'm willing to program these changes myself and submit a patch. I just
wanted to see what the general consensus is before I started.

Matt
Re: Reactions to CompositeTable API [message #570923 is a reply to message #18825] Fri, 01 December 2006 17:37 Go to previous message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
Matthew Hall wrote:
> A snippet's worth a thousand words:

Agreed. How's this?

/**
* A CompositeTable editing first/last name pairs
*
* @author djo
*/
public class CompositeTableSnippet2 {
// First some data to edit...
private static class Name {
public String first;
public String last;
public Name(String first, String last) {
this.first = first;
this.last = last;
}
}

static Name[] swtCommitters = new Name[] {
new Name("Grant", "Gayed"),
new Name("Veronika", "Irvine"),
new Name("Steve", "Northover"),
new Name("Mike", "Wilson"),
new Name("Christophe", "Cornu"),
new Name("Lynne", "Kues"),
new Name("Silenio", "Quarti"),
new Name("Tod", "Creasey"),
new Name("Felipe", "Heidrich"),
new Name("Billy", "Biggs"),
new Name("B", "Shingar")
};

// Now, define the table's header and row objects
//
// A tabular layout is desired, so no layout manager is needed
// on the header
// or row. CompositeTable will handle the layout automatically.
// However,
// if you supply a layout manager, CompositeTable will respect
// and use it.

private static class Header extends Composite {
public Header(Composite parent, int style) {
super(parent, style);
new Label(this, SWT.NULL).setText("First Name");
new Label(this, SWT.NULL).setText("Last Name");
}
}

private static class Row extends Composite {
public Row(Composite parent, int style) {
super(parent, style);
firstName = new Text(this, SWT.NULL);
lastName = new Text(this, SWT.NULL);
}
public final Text firstName;
public final Text lastName;
}

// Where it all starts...

public static void main (String [] args) {
Display display = new Display ();
Shell shell = new Shell (display);
shell.setLayout(new FillLayout());

CompositeTable table = new CompositeTable(shell, SWT.NULL);
new Header(table, SWT.NULL); // Specify Header and Row
new Row(table, SWT.NULL);
table.setRunTime(true);
table.setNumRowsInCollection(swtCommitters.length);

// Note the JFace-like virtual table API
table.addRowContentProvider(new IRowContentProvider() {
public void refresh(CompositeTable sender,
int currentObjectOffset,
Control rowControl)
{
Row row = (Row) rowControl;

row.firstName.setText(swtCommitters[currentObjectOffset].fir st);
row.lastName.setText(swtCommitters[currentObjectOffset].last );
}
});

table.addRowFocusListener(new RowFocusAdapter() {
public void depart(CompositeTable sender,
int currentObjectOffset, Control rowControl) {
Row row = (Row) rowControl;

swtCommitters[currentObjectOffset].first = row.firstName.getText();
swtCommitters[currentObjectOffset].last = row.lastName.getText();
}
});

shell.setSize(500, 150);
shell.open ();
while (!shell.isDisposed()) {
if (!display.readAndDispatch ()) display.sleep ();
}
display.dispose ();

// Print the results
for (int i = 0; i < swtCommitters.length; i++) {
System.out.println(swtCommitters[i].first + " " +
swtCommitters[i].last);
}
}
}

If this can be (a) simplified, or (b) made cleaner by introducing a
CompositeTableItem, I'm interested. :-) (sincerely)

Your second point relates to the question of using factories versus
custom Composites. I actually wrote an earlier version of
CompositeTable this way, and I have two answers to this:

1) Using custom Composites to create custom SWT controls is the SWT way
of doing things (CCombo, etc...).

2) Using custom Composites encourages folks to design objects that can
stand alone. Using factories doesn't scale; you wind up with things like:

public static NameAndAddressControls
buildNameAndAddressComposite(Composite parent) {...}

and then to make matters worse, when you want to bind, you often wind up
with methods like:

public static void bindNameAndAddressControls(NameAndAddressControls
bigBagOSWTControls, Object person, String firstNameProperty, String
lastNameProperty, String address1Property, String cityProperty, String
stateProperty, String zipProperty) {...}

And where do you put these methods? They don't clearly belong to any
particular class.

So the resulting design isn't object oriented, isn't extensible, is hard
to follow, and so on.

So I'm actually pretty deeply concerned about folks doing RCP falling
into this trap. I've personally been there, done that, and have the
scars to prove it. Having an interface supplying public Control
createControl() is OK for a View, but I don't think it should be
generalized to all UI constructs.

What do I recommend doing instead?

Make an Address object that extends Composite. It can be used as the
row object inside a CompositeTable or it can stand on its own. It then
becomes the logical place for a bindAddress() method if you want one, or
if you want a strict MVC separation, you can bind in your controller
tier and just have getters for each of the SWT controls that need binding.


Best regards,

Dave Orme

PS: The above snippet and several others are in CVS. I'm working on
getting a real build out RSN.

>
> 
> CompositeTable table = new CompositeTable(parent, SWT.VIRTUAL | 
> SWT.BORDER);
> 
> // I like the class as a manager for the row, I just don't think it
> // should extend Composite by design
> // Adding this interface will remove all that reflection code
> interface ICompositeRow {
>   // Implementers are responsible for making getControl() return the
>   // created control
>   void createControl(CompositeTable table);
>   Control getControl();
> }
> 
> abstract class CompositeRow implements ICompositeRow {
>   Control control;
> 
>   Control getControl() {
>     return control;
>   }
> 
>   /** Sets the control returned by getControl */
>   void setControl(Control control) {
>     this.control = control;
>   }
> }
> 
> class MyHeader extends CompositeRow {
>   Label first;
>   Label last;
> 
>   void createControl(CompositeTable table) {
>     Composite composite = new Composite(table, SWT.NONE);
>     first = new Label(composite, SWT.NONE);
>     last = new Label(composite, SWT.NONE);
>     first.setText("First");
>     last.setText("Last");
>     setControl(composite);
>   }
> }
> 
> table.setHeaderProvider(new IRowProvider() {
>   ICompositeRow createRow() { return new MyHeader(); }
> });
> 
> class MyRow implements ICompositeRow {
>   Text first;
>   Text last;
> 
>   void createControl(CompositeTable table) {
>     Composite composite = new Composite(table, SWT.NONE);
>     first = new Text(composite, SWT.BORDER);
>     last = new Text(composite, SWT.BORDER);
>     setControl(composite);
>   }
> }
> 
> table.setRowProvider(new IRowProvider() {
>   ICompositeRow createRow() { return new MyRow(); }
> });
> 
> // The CompositeItem is basically the JFace wrapper around the content
> abstract class CompositeItem extends Item {
>   CompositeItem(CompositeTable table, int style) {
>     super(table, style);
>     table.addItem(this);
>   }
> 
>   CompositeItem(CompositeTable table, int style, int index) {
>     super(table, style);
>     table.addItem(this, index);
>   }
> 
>   // This property is managed by CompositeTable as it scrolls up
>   // and down
>   ICompositeRow row = null;
>   ICompositeRow getRow() { return row; }
>   void setRow(ICompositeRow row) {
>     if (this.row != null)
>       unhookListeners(this.row);
> 
>     this.row = row;
>     updateRow();
> 
>     if (row != null)
>       hookListeners(row);
>   }
> 
>   // These methods may be over-designed, but just a thought
>   // off the top of my head
>   // DataBinding would really help here
>   abstract void hookListeners(ICompositeRow row);
>   abstract void unhookListeners(ICompositeRow row);
>   abstract void updateRow();
> }
> 
> class MyItem extends CompositeItem implements Listener {
>   Name name = null;
> 
>   MyItem(CompositeTable table, int style) {
>     super(table, style);
>   }
> 
>   MyItem(CompositeTable table, int style, int index, Name name) {
>     super(table, style, index);
>   }
> 
>   Name getName() { return name; }
>   void setName(Name name) {
>     this.name = name;
>     updateRow();
>   }
> 
>   void hookListeners(ICompositeRow row) {
>     MyRow r = (MyRow) row;
>     r.first.addListener(SWT.Modify, this);
>     r.last.addListener(SWT.Modify, this);
>   }
> 
>   void unhookListeners(ICompositeRow row) {
>     MyRow r = (MyRow) row;
>     r.first.removeListener(SWT.Modify, this);
>     r.last.removeListener(SWT.Modify, this);
>   }
> 
>   void updateRow() {
>     MyRow r = (MyRow) getRow();
>     if (r == null) return;
>     r.first.setText(name == null ? "" : name.getFirst());
>     r.last.setText(name == null ? "" : name.getLast());
>   }
> 
>   void handleEvent(Event e) {
>     if (name == null) return;
> 
>     MyRow row = (MyRow) getRow();
>     if (e.widget == row.first)
>       name.setFirst(row.first.getText());
>     else if (e.widget == row.last)
>       name.setLast(row.last.getText());
>   }
> }
> 
> table.setItemProvider(new ICompositeItemProvider() {
>   CompositeItem createItem(CompositeTable table, int style, int index) {
>     return new MyItem(table, style, index);
>   }
> });
> 
> table.addListener(SWT.SetData, new Listener() {
>   void handleEvent(Event e) {
>     MyItem item = (MyItem) e.item;
>     int index = table.indexOf(item);
>     item.setName(Names.get(index));
>   }
> });
> 
> table.setItemCount(Names.getCount());
> 
> 

>
> This is just a rough sketch of what I had in mind.
>
>> 1) The *Item concept in SWT mainly represents what *data* will be
>> placed in the specified columns, along with some layout information
>> (width, etc).
>>
>> 2) My understanding is that the SWT table in SWT.VIRTUAL mode creates
>> items for *all* rows that have been displayed and then never destroys
>> them.
>
> As outlined above, an Item is a separate concept from a Row. The item
> maps to the data, where the Row maps to the visible display.
>
>> If I called it setItemCount, this would imply that if you
>> setItemCount(1000000), that there would be a million
>> CompositeTableItem objects somewhere, which simply isn't true.
>
> Not necessarily. This behavior could be emulated and items created on
> the fly as they are needed for display by the ICompositeItemProvider,
> and initialized by the SWT.SetData listener.
>
> It would also be useful to have SWT.VIRTUAL be an option instead of a
> given. This would allow users to just instantiate their items as needed
> for small collections, which would result in simpler code:
>
>
> for (int i = 0; i < Names.getCount(); i++)
>   new MyItem(table, SWT.NONE).setName(Names.get(i));
> 

>
>>> I don't like the design-mode / active-mode paradigm.
>>
>> Neither do I.
>>
>> There are two reasons this exists: One major goal I had when creating
>> CompositeTable is that it would be simple to use within Visual Editor.
>>
>> I could use Beans.isDesignTime() in the control and maybe I should do
>> that, but I wanted the control behave inside VE exactly the way it
>> behaves at run-time. This way you can more easily learn to use the
>> control by changing the properties interactively in VE and watching
>> what happens.
>>
>> The only way to accomplish this is to have a property that explicitly
>> switches the control from design-time behavior to run-time behavior.
>>
>> The second reason is that JavaBeans isn't in Foundation profile. So
>> in order to support Foundation, I can't use Beans.isDesignTime().
>>
>> But maybe this property was a bad idea.
>>
>> I'd be happy for feedback on this. What do folks think?
>>
>
> Perhaps make the property false by default? The design changes I'm
> suggesting would not prevent this option, but it is a little jarring to
> have this setDesignTime(false) method call in the middle of my code.
>
>>> Then there is the use of reflection. Although I recognize that Dave
>>> Orme (who authored the control) would be quite comfortable with
>>> reflection, given his role in VE and data binding, I am nonetheless
>>> uncomfortable with it. Using reflection is a performance hit, is
>>> brittle, and really isn't necessary if we just invent an interface to
>>> replace it (ICompositeRowBuilder). Moreover it makes adoption into
>>> SWT impossible since (as I understand it) reflection is not available
>>> in the CDC-1.0/Foundation-1.0 runtime environment.
>>
>> There is a really good question here, but a few misconceptions too.
>> I'll clear away the misconceptions first, and then we can hopefully
>> tackle the underlying question more productively:
>>
>> 1) On Foundation support: reflection is there but not dynamic proxies
>> or JavaBean support.
>
> Good to know
>
>>
>> 2) Regarding performance, reflection is only used to construct new row
>> controls. But once a row control is constructed, it is never
>> destroyed until the entire CompositeTable control is destroyed.
>> (Instead, CompositeTable recycles row objects.) So if your table has
>> 20 rows of data in it, there will be exactly 20 reflection calls the
>> first time your data is displayed and no more reflection calls after
>> that. Since reflection is never used any more after the row controls
>> are constructed, performance just isn't an issue here.
>
> True, but a regular old java interface like IRowProvider is much more
> comfortable to Java programmers than duck typing.
>
>> 3) I don't understand how reflection is brittle in this case?
>
> It excludes the possibility of other constructor signatures, such as
> MyCompositeRow(CompositeTable table) where the style bit is implicit.
> Although considered bad form in SWT, this is a legitimate choice for the
> developer.
>
>> Now on to the underlying question (the whole reason I use reflection
>> to begin with):
>>
>>> And I REALLY don't like being forced to extend composite for my rows,
>>> when we could just define an interface that creates and manages a
>>> composite instead. This is a very Swing way of using SWT.
>>
>> As stated above, a design goal for CompositeTable was to be able to
>> edit the table visually using Visual Editor. Visual Editor knows how
>> to edit a custom Composite, but not how to edit a JFace-like
>> createControl() UI factory.
>
> The JFace createControl() factory paradigm is pervasive throughout the
> platform. I think the "knows how to edit" use case really belongs in
> VE, not in each control we hope to use in VE.
>
>> However, I would like to be able to accommodate folks that would
>> prefer to use an interface. If someone can propose an API that makes
>> sense and doesn't lose the VE support, I'd be very glad to listen.
>
> Perhaps you could point me to some HOWTO's or tutorials for teaching VE
> how to design custom controls, and I'll help you work on it.
>
>>> It would also seem more appropriate to use SWT.SetData listeners like
>>> the other virtual controls instead of addRowContentProvider.
>>
>> Again, it's a possibility to try to mimic the SWT names, but don't you
>> feel that folks will be confused here?
>
> That's a question for the bystanders!
>
> Maybe it would help if we following Steve Northover's advice and set the
> SWT.SMART bit on the CompositeTable. :)
>
>> In CompositeTable's event, one normally doesn't set data into some
>> *Item object, but rather sets data into real SWT controls in your row
>> object or possibly uses data binding to bind those controls to a
>> domain model object.
>
> Sorry, I should have explained that in my original post. In my proposed
> design the concrete CompositeItem subclass is responsible for populating
> the ICompositeRow fields and managing the binding between those
> controls. This is a departure from SWT conventions, but as you say this
> is a different beast, and I felt it was the least "weird" of approaches.
> Your mileage my vary.
>
>> What CompositeTable does here seems closer conceptually to the JFace
>> content provider concept, which is why this name was chosen.
>>
>> I'm willing to rename this, but I'm concerned about confusion.
>
> To me this design feels a lot clearer and simpler, but I acknowledge
> that this may be confusing to others.
>
>> In balance, CompositeTable tries to reflect and synthesize ideas from
>> all of SWT + JFace + Visual Editor + Eclipse Data binding APIs. My
>> hope is that this will make folks more productive and result in more
>> maintainable applications.
>
> Thanks Dave for taking the time to respond.
>
> Matthew
Re: Reactions to CompositeTable API [message #571063 is a reply to message #18982] Fri, 01 December 2006 17:58 Go to previous message
Chris Gross is currently offline Chris GrossFriend
Messages: 471
Registered: July 2009
Senior Member
Hi Matt,

Just to be clear, I didn't mean to imply that what you were asking was
unreasonable. Not at all. I can see how your changes would make sense
(though admittedly I'm not well versed in CompositeTable and haven't
looked hard at your changes). I just wanted to figure out what about
CompositeTable was really exciting you (exciting enough that you are
willing to spend time talking about these changes). I was just curious
is all.

Regards,
-Chris

Matthew Hall wrote:
> Chris Gross wrote:
>> Can I ask a (perhaps dumb) question? You seem to want to change a lot
>> of the CompositeTable API and make it fit in better with SWT, etc.
>
> I'm not trying to rock the boat here. David Orme himself said that he
> want to avoid confusing users. I'm making these suggestions because I
> think it will make the control simpler and more intuitive. And I'm not
> suggesting that my ideas are the best--I'm trying to get a dialog going.
>
>> With all these changes wouldn't the end result be much like a regular
>> SWT Table that is populated with widgets using TableEditors (except
>> that the editors are only created on visible rows)? In other words,
>> it sounds like alot of what you don't like is what makes
>> CompositeTable unique.
>
> Not really. I'm suggesting changes to the API to make what
> CompositeTable does more accessible to SWT programmers. The
> reservations I have are:
>
> * I dislike reflection because however you use reflection becomes de
> facto API, except the compiler can't check for bad usage. Who knows if
> somebody will refactor your Row class down the road, not knowing it
> *has* to have a (Composite, int) constructor? The compiler will *never*
> catch this. A documented interface instead of reflection will avoid
> this problem. Besides, it may be possible to just have the default
> IRowProvider perform this exact behavior so that current CompositeTable
> users can just keep doing prototyping if they prefer.
> * SWT programmers are used to working with *Items. Working with items
> the non-virtual way is much easier than the virtual way, and I would
> like an option between the two.
> * Renaming some of the API (numRowsInCollection == itemCount) to match
> SWT naming conventions will make using this control more intuitive.
>
>> What is the feature (or features) from CompositeTable that you think
>> are the killer (i.e. killer in a good way ;)?
>
> * The ability to use controls at all times, instead of having to click
> the cell to bring up the editor.
> * The ability to lay out those controls any way you like within the row
> if the standard left-to-right columnar layout doesn't suit you.
>
> I'm willing to program these changes myself and submit a patch. I just
> wanted to see what the general consensus is before I started.
>
> Matt
Re: Reactions to CompositeTable API [message #571086 is a reply to message #18982] Fri, 01 December 2006 18:24 Go to previous message
Thomas Schindl is currently offline Thomas SchindlFriend
Messages: 5487
Registered: July 2009
Senior Member
[...]
> * The ability to use controls at all times, instead of having to click
> the cell to bring up the editor.

TableViewer/TreeViewer will hopefully also support this kind of feature
in 3.3 timeframe (I'm working on it currently). Tabing support is
already in the latest nightly build if you are interested.

https://bugs.eclipse.org/bugs/show_bug.cgi?id=166383
Usage is shown in this snippet:
http://dev.eclipse.org/viewcvs/index.cgi/%7Echeckout%7E/org. eclipse.jface.snippets/Eclipse%20JFace%20Snippets/org/eclips e/jface/snippets/viewers/Snippet025TabEditing.java

Keyboard navigation in Tables will follow in 3.3M4 or 3.3M5.

Tom

[...]
Re: Reactions to CompositeTable API [message #571115 is a reply to message #18982] Fri, 01 December 2006 19:31 Go to previous message
Dave Orme is currently offline Dave OrmeFriend
Messages: 424
Registered: July 2009
Senior Member
1) THANKS again for wanting to contribute.

2) I think I replied to your other concerns in the other reply except
for one: reflection.

To this, I reply: SWT controls will *never* deviate from having (parent,
style) as long as Steve Northover is SWT lead. ;-)


Regards,

Dave Orme

Matthew Hall wrote:
> Chris Gross wrote:
>> Can I ask a (perhaps dumb) question? You seem to want to change a lot
>> of the CompositeTable API and make it fit in better with SWT, etc.
>
> I'm not trying to rock the boat here. David Orme himself said that he
> want to avoid confusing users. I'm making these suggestions because I
> think it will make the control simpler and more intuitive. And I'm not
> suggesting that my ideas are the best--I'm trying to get a dialog going.
>
>> With all these changes wouldn't the end result be much like a regular
>> SWT Table that is populated with widgets using TableEditors (except
>> that the editors are only created on visible rows)? In other words,
>> it sounds like alot of what you don't like is what makes
>> CompositeTable unique.
>
> Not really. I'm suggesting changes to the API to make what
> CompositeTable does more accessible to SWT programmers. The
> reservations I have are:
>
> * I dislike reflection because however you use reflection becomes de
> facto API, except the compiler can't check for bad usage. Who knows if
> somebody will refactor your Row class down the road, not knowing it
> *has* to have a (Composite, int) constructor? The compiler will *never*
> catch this. A documented interface instead of reflection will avoid
> this problem. Besides, it may be possible to just have the default
> IRowProvider perform this exact behavior so that current CompositeTable
> users can just keep doing prototyping if they prefer.
> * SWT programmers are used to working with *Items. Working with items
> the non-virtual way is much easier than the virtual way, and I would
> like an option between the two.
> * Renaming some of the API (numRowsInCollection == itemCount) to match
> SWT naming conventions will make using this control more intuitive.
>
>> What is the feature (or features) from CompositeTable that you think
>> are the killer (i.e. killer in a good way ;)?
>
> * The ability to use controls at all times, instead of having to click
> the cell to bring up the editor.
> * The ability to lay out those controls any way you like within the row
> if the standard left-to-right columnar layout doesn't suit you.
>
> I'm willing to program these changes myself and submit a patch. I just
> wanted to see what the general consensus is before I started.
>
> Matt
Re: Reactions to CompositeTable API [message #571133 is a reply to message #19240] Fri, 01 December 2006 20:53 Go to previous message
Matthew Hall is currently offline Matthew HallFriend
Messages: 368
Registered: July 2009
Senior Member
> To this, I reply: SWT controls will *never* deviate from having (parent,
> style) as long as Steve Northover is SWT lead. ;-)

Touché
Re: Reactions to CompositeTable API [message #572081 is a reply to message #19061] Sun, 10 December 2006 06:06 Go to previous message
Al Major is currently offline Al MajorFriend
Messages: 72
Registered: July 2009
Member
Tom Schindl wrote:
> [...]
>> * The ability to use controls at all times, instead of having to click
>> the cell to bring up the editor.
>
> TableViewer/TreeViewer will hopefully also support this kind of feature
> in 3.3 timeframe (I'm working on it currently). Tabing support is

any timeframe on this as yet? is there a bug number that i can track?
i'd be happy to test any functionality you put out there. if this is
done comprehensively (there's a few life cycle events that i've pointed
out in discussions on CTableTree), it may be enough for my current needs.

thx,

al
Previous Topic:Can a CompositeTable have more than 2 columns?
Next Topic:CompositeTable doesn't provide a JFace-Viewer-API
Goto Forum:
  


Current Time: Fri Dec 19 14:37:24 GMT 2014

Powered by FUDForum. Page generated in 0.03737 seconds
.:: Contact :: Home ::.

Powered by: FUDforum 3.0.2.
Copyright ©2001-2010 FUDforum Bulletin Board Software