[bloc] shape size?

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
69 messages Options
1234
Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Thierry Goubier
Hi Alex, Igor and others,

this discussion is interesting to follow. GUI frameworks are hard...

Le 03/04/2016 16:58, Aliaksei Syrel a écrit :

>     And you lost me here.. That is complete nonsense.. from any perspective.
>     Can i unsee this code, please? :)
>
>
> If I would say that we have defaultShape method and it can be overridden as:
>
>     defaultShape
>       ^ BlShape new
>          fillPaint: (BlColorPaint new color: (Color yellow));
>          path: BlRectanglePath new
>
> would it make you happy?

If you don't tell me there is a cost for creating a shape in athens,
I'll wonder if you're not asking me to optimise by caching a shape; and
that is over-engineering.

>
>     .. to me it feels like: okay, what we need to do, to prevent
>     overrides of our beloved default #drawOn: method.
>
> You are wrong concerning preventing to override drawOn :)

I wonder if that "shape" thing is not something like the difference
between Roassal and Trachel: RT vs TR objects. And, yes, for me, the
RT/TR hierarchy is a reimplementation of objects over Athens, and the
end result is that it is easy to compose existing objects in Roassal and
hard to extend it.

> Don't forget that there was a customer *requirement* concerning bloc:
>
> Can we change how morph looks on fly? Can we create a rectangle morph
> and change it's shape from rectangle to circle? Because it can nicely
> show while presenting that *Pharo is live system*. I'm pretty sure Stef
> said it once ago.

If that is your requirement, then this is bad.

It's a demo requirement with costly consequences. Does it apply in real
life in a system where recreating a complete Morph is so cheap (witness
FastTable!)? I'd say no.

> Do you see how bloc story can nicely be told:
>
>     We have basic UI elements and each element has shape that can be
>     easily changed live. Shape is defined by a path which can be filled
>     or stroked using a paint. Complex elements can be created as
>     composition of elements with basic shapes (rectangle, circle).
>
>
> Isn't it beautiful? :)

It is, but it tells of complexity: UI behavior composition (not only
graphics). Extending elements may also require extending shapes and
understanding how they interact and compose.

Regards,

Thierry

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Igor Stasenko
In reply to this post by Aliaksei Syrel


On 3 April 2016 at 19:23, Aliaksei Syrel <[hidden email]> wrote:
This means that any abstraction/wrapper around athens will fail.

I would not say it like that. WIth decent effort you can do it. But the right question here: do you really need it?
You missing some features for shapes? Good.. make new one(s) , just teach them how to draw themselves on Athens canvas and you done. 

For instance, for using shape in UI test it missing, #containsPoint: behavior. 
And for clipping, it missing 
  clipOn: aCanvas during: aBlock 
behavior.
So, you can choose to either extend basic protocol in Athens by implementing this feature(s) for all existing shapes, or introduce own shapes, polymorphic with AthensShape(s) but in addition implementing these protocols.
Then you can use same shape for drawing, clipping and UI testing. Job done.
You basically missing those two methods and you are done.
And instead you inventing something that not only solves the problem, but puts a lot of restrictions on what you can draw using Block and how.
 
What if we would remove drawingShape and by default leave drawOn: method to be empty. That way we would not put any constraints on rendering part. user just gets athens canvas and can do whatever she wants.

Well, a root morph cannot put any assumptions how his subclasses would want to draw themselves.. So, really, no assumptions means empty method.
Sounds good to me. Well, it is empty, and just server as a placeholder indicating a protocol and a point of customization, nothing else. (Stef will most probably force you to put a nice comment there ;)
 
Instead we would have only clipping shape and event area shape.
What do you think? :)

That's what i proposing. What i think i already wrote in this thread :)
It is up to you to accept or reject the idea. Or propose something even better and simpler. Or by any other participants of discussion.
And why you surrender so fast? What if i am wrong? What is going on?
Lets make it as best as we can, not 'as Igor says'.  :)


Cheers,
Alex

On Sun, Apr 3, 2016 at 6:04 PM, Igor Stasenko <[hidden email]> wrote:


On 3 April 2016 at 17:58, Aliaksei Syrel <[hidden email]> wrote:
And you lost me here.. That is complete nonsense.. from any perspective.
Can i unsee this code, please? :)

If I would say that we have defaultShape method and it can be overridden as:

defaultShape
 ^ BlShape new
    fillPaint: (BlColorPaint new color: (Color yellow));
    path: BlRectanglePath new
would it make you happy?

Nope. (see bottom of reply why)
 
 .. to me it feels like: okay, what we need to do, to prevent overrides of our beloved default #drawOn: method.
You are wrong concerning preventing to override drawOn :)
Don't forget that there was a customer requirement concerning bloc:

Can we change how morph looks on fly? Can we create a rectangle morph and change it's shape from rectangle to circle? Because it can nicely show while presenting that Pharo is live system. I'm pretty sure Stef said it once ago.

Do you see how bloc story can nicely be told:
We have basic UI elements and each element has shape that can be easily changed live. Shape is defined by a path which can be filled or stroked using a paint. Complex elements can be created as composition of elements with basic shapes (rectangle, circle). 

Isn't it beautiful? :)

Nope. Because it would be beautiful, if your statements would be reflected in
reality and by reality.
In your example #defaultShape method, you simply isolating some behavior into a separate method. It does not changes anything.

You want to achieve to be able to change shapes on the fly. Good. A honourable goal. And welcoming. No objections here.

But can we achieve it without losing being able to change the color of shape on the fly. Please? :)
The way you introducing it goes straightly into conflict with: i want to be able to draw anything, the way i feel and like. 
You proposing a bad trade: oh yeah, you wanted to change shapes on the fly.. good.. but at cost of unable to draw anything else than simple rectangles in simple order.. 
Well.. i am not buying such trade. Can you sweeten a deal?

The point is, that shape is not the only thing you need to put into equation in order to get thing on the screen.. You also need paint. And that's the reason why you have  
fillPaint: (BlColorPaint new color: (Color yellow));

(lets put aside the hardcoding of color in unrelated place (defaultShape).. for the sake of example)
but does that fully covers all and any possible ways and needs of drawing?
Nope! Again not..
And voila, say welcome to composite "shapes" or "elements" or call it as you like it.
But does that fully covers all and any possible ways you can draw something with Athens?
Nope, it is not. Again. Sorry. You can achieve that only if you completely encode all possible operations and features provided by Athens using some kind of command pattern and put them in 'element' or 'compositeElement' or 'compositeOfCompositeElementsComposition' whatever.

For instance, how you going to encode AthensPaintMode into your elements? 
I guess you will offer to kill it with your 'it is not used so often' knife.

Can't you see that you basically creating a wrapper for all Athens feature set. 
I can tell you that you wasting effort: you cannot get anything extra by doing it. Except from extra complexity.
And for what? Something that already there and can be used out of the box.

If you don't like Athens API - go on, and change it. Make it better and more convenient to use. But encapsulating all possible combinations of all possible drawing operations? Good luck with that.


Cheers,
Alex

On Sun, Apr 3, 2016 at 3:37 PM, Igor Stasenko <[hidden email]> wrote:


On 3 April 2016 at 16:20, Igor Stasenko <[hidden email]> wrote:


On 3 April 2016 at 15:28, Glenn Cavarlé <[hidden email]> wrote:
Hi,

Aliaksei Syrel wrote
> However, in most UI of applications (in web, mobile) it is extremely rare
> that clipping or event handling areas differ from drawing one (visual one
> -
> one that user sees in the end).

It is the same for desktop UI (Qt, JavaFx,...).

I think the misunderstanding come from "shape", so let us forget BlShape and
concentrate on BlElement.

In fact, using Bloc now, If we want a Rectangle with an clickable inner
Circle, we have to defined 2 elements, the Rectangle one and the Circle one
(subclass of BlElement or using script style).
The CircleElement must be the child of the RectangleElement but we don't
have to override any method or to rewire CircleElement events back to its
parent, we just need to add an event listener to the CircleElement from
where we want.
It is the same with a Text in a Rectangle, we need a BlElement for the Text
and another for the Rectangle in order to compose them and to position the
Text in the Rectangle.

For me its like defining a CircleButton in a RectanglePanel with any other
ui libraries, i can do that by subclassing Panel or by using script style.
But i have to manipulate 2 elements and it makes sense for me.

Bloc does not provide user-friendly high-level abstractions at BlShape or
BlElement level like BlCircleShape or BlCircleElement.
I don't know if it is the right place to add them but it is clearly a point
of misunderstanding when people uses Bloc.
 
 
It seems to me that Bloc is not made to be used direclty as a graphical
framework but it is a librarie to build more user-friendly graphical
framework.
Shape, Path, ... are implementations stuff, most of users should not care
about that using a "framework".

Thanks for explanation.. 
Now i have a hard time understanding, what is the purpose of so-called 'element'. Element of what? What its role?
What its interaction between morphs and shapes, and what you see & feel on the screen?

From your description, what i can tell is that it is completely unnecessary.
You have morphs to define hierarchy/composition.
And you can use shapes to define geometry for UI/clipping.
As for drawing - there's no need to put any constraints, you don't have to even mention that there are shapes involved. It is indeed, an implementation detail from that perspective, since you drawing things using Athens, and it uses shapes to define affected regions. But that completely orthogonal to what happens at UI level.
Thus, it is very surprising to me see following code snippet:


BlCell>>initialize
    super initialize.
    self
        shape:
            (BlShape new
                fillPaint: (BlColorPaint new color: (Color yellow));
                path: BlRectanglePath new);
        extent: self extent

because it is really seems like encapsulation of what you gonna draw.. 
and putting it into #initialize method in some form? 

And you lost me here.. That is complete nonsense.. from any perspective.
Can i unsee this code, please? :)

<acid mode on>
.. to me it feels like: okay, what we need to do, to prevent overrides of our beloved default #drawOn: method.

And you talking about 'sophistication' after that?
 
</acid mode off>

 
 
PS: @Alex, what are the planned refactoring? I'm lost in the new intentions
and in the roadmap of Bloc...
Regards,
Glenn.



-----
Glenn Cavarlé
--
View this message in context: http://forum.world.st/bloc-shape-size-tp4887929p4888039.html
Sent from the Pharo Smalltalk Developers mailing list archive at Nabble.com.




--
Best regards,
Igor Stasenko.



--
Best regards,
Igor Stasenko.




--
Best regards,
Igor Stasenko.




--
Best regards,
Igor Stasenko.
Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Thierry Goubier
In reply to this post by stepharo
Le 03/04/2016 17:33, stepharo a écrit :

> If you want to change clicking behaviour you need to override one single
> method.
>>
>>         Everything you wrote with unreadable amount of characters is
>>         for nothing.
>>
>>     I see clearly point of Igor. And for me it feels very logical.
>>     With such design you can lively change clipping area and
>>     interaction area for any morph (element) on screen.
>>
>>
>> In short, i see only two cases where indeed, morph requires a nothing
>> of shapes to define:
>>  - clipping region(s)
>>  - ui interaction region(s)
>>
>> but for drawing? nooooo... really? who cares what you draw there?
>> draw anything, in any possible way you see fit.. compose, decompose,
>> recombine, blend and mix.. that's the whole purpose of drawing and be
>> artistic and be able to express yourself in any possible way you want :)
>> Why nailing and formalizing things that are tend to be hardly
>> formalizable and more than that, unnecessary.
>> That's my main concern about current design.
>
> I agree.
> I do not see why people are forced to create a submorph just to change
> the rendering.
> If you want to change it dynamically you can for example pass a
> different shape.

I don't see the problem with subclassing a morph.

The reverse: I feel like current Morphs are huge monsters of
configurability and parameter blocks and properties and intricated code
and thousands of methods so that one doesn't has to subclass...

Simpler, "subclassable" morphs suits me a lot better.

Bloc looks like its taking some of the bad aspects of Morphic.

Regards,

Thierry

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Igor Stasenko


On 3 April 2016 at 19:48, Thierry Goubier <[hidden email]> wrote:
Le 03/04/2016 17:33, stepharo a écrit :
If you want to change clicking behaviour you need to override one single
method.

        Everything you wrote with unreadable amount of characters is
        for nothing.

    I see clearly point of Igor. And for me it feels very logical.
    With such design you can lively change clipping area and
    interaction area for any morph (element) on screen.


In short, i see only two cases where indeed, morph requires a nothing
of shapes to define:
 - clipping region(s)
 - ui interaction region(s)

but for drawing? nooooo... really? who cares what you draw there?
draw anything, in any possible way you see fit.. compose, decompose,
recombine, blend and mix.. that's the whole purpose of drawing and be
artistic and be able to express yourself in any possible way you want :)
Why nailing and formalizing things that are tend to be hardly
formalizable and more than that, unnecessary.
That's my main concern about current design.

I agree.
I do not see why people are forced to create a submorph just to change
the rendering.
If you want to change it dynamically you can for example pass a
different shape.

I don't see the problem with subclassing a morph.

Me neither. But do you confusing subclassing and submorph compositing? 
 
The reverse: I feel like current Morphs are huge monsters of configurability and parameter blocks and properties and intricated code and thousands of methods so that one doesn't has to subclass...

Agree, the Morph protocol is bloated. And i don't like it too.
That is a result of lifting features and properties up in inheritance chain.
And i can imagine how it happens over time:
- we have a morph.. 
- hurray!
- can we have a morph with a border?
- yes! Here BorderedMorph for you!
- nice.. but can i use border in another subclass of Morph?
- yes! Here borderStyle: property for you.. (and BorderedMorph is now useless)

Or take a layout.. We could have , say, MorphWithLayout class. That introducing layouts. While other, simpler morph don't. Really, what layout you need in a morph that contains a plain rectangle fully covering its bounds?
Or even 'having submorphs'. We could have MorphWithSubmorphs. Which could introduce submorphs concept. 

Separation of concerns. Good way to go. But if you need to have a morph that both has layout and border, then you are in trouble: you forced to do one of following:
 - make own Morph subclass, duplicating features of both.. or make a composition of submorphs that will represent both features, or... lift both features to the top of inheritance chain, getting bloat as result.
Most of the times, most of things are achiveable through composition..
but some of them.. like drawing - apparently not.
 
In any case i agree, that many features, that Morph proposing out of the box needs review and validation in terms, what if we isolate certain feature(s) in separate subclass and provide them via composition.


Simpler, "subclassable" morphs suits me a lot better.

Bloc looks like its taking some of the bad aspects of Morphic.

One step at a time. You cannot fix all the problems of parent at once.
The way how Bloc born, i think (i may be mistaken), it is a 'clean and lean' port of Morphic. But of course Morphic is huge monster, and porting such monster while rewriting its complex logic at the same time could be daunting hard.
In any case, i think it is better. Let us hope, it will be even better.
 
Regards,

Thierry




--
Best regards,
Igor Stasenko.
Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Igor Stasenko
In reply to this post by Thierry Goubier


On 3 April 2016 at 19:43, Thierry Goubier <[hidden email]> wrote:
Hi Alex, Igor and others,

this discussion is interesting to follow. GUI frameworks are hard...

Le 03/04/2016 16:58, Aliaksei Syrel a écrit :
    And you lost me here.. That is complete nonsense.. from any perspective.
    Can i unsee this code, please? :)


If I would say that we have defaultShape method and it can be overridden as:

    defaultShape
      ^ BlShape new
         fillPaint: (BlColorPaint new color: (Color yellow));
         path: BlRectanglePath new

would it make you happy?

If you don't tell me there is a cost for creating a shape in athens, I'll wonder if you're not asking me to optimise by caching a shape; and that is over-engineering.

Of course, creating shapes has own cost, as anything else. But, guess what, you having caching mechanism in Athens out of the box, if you don't happy with performance. 




    .. to me it feels like: okay, what we need to do, to prevent
    overrides of our beloved default #drawOn: method.

You are wrong concerning preventing to override drawOn :)

I wonder if that "shape" thing is not something like the difference between Roassal and Trachel: RT vs TR objects. And, yes, for me, the RT/TR hierarchy is a reimplementation of objects over Athens, and the end result is that it is easy to compose existing objects in Roassal and hard to extend it.

Sad. Sarcasm tries to flow from my tongue. But i will keep my mouth shut. No comments :)
 

Don't forget that there was a customer *requirement* concerning bloc:

Can we change how morph looks on fly? Can we create a rectangle morph
and change it's shape from rectangle to circle? Because it can nicely
show while presenting that *Pharo is live system*. I'm pretty sure Stef
said it once ago.

If that is your requirement, then this is bad.

It's a demo requirement with costly consequences. Does it apply in real life in a system where recreating a complete Morph is so cheap (witness FastTable!)? I'd say no.

Do you see how bloc story can nicely be told:

    We have basic UI elements and each element has shape that can be
    easily changed live. Shape is defined by a path which can be filled
    or stroked using a paint. Complex elements can be created as
    composition of elements with basic shapes (rectangle, circle).


Isn't it beautiful? :)

It is, but it tells of complexity: UI behavior composition (not only graphics). Extending elements may also require extending shapes and understanding how they interact and compose.

That is road to nowhere. You already having morphs for composition. No need to introduce 'elements' to compose something inside composition of morphs.. 
If you cannot do something out of composition of morphs, what makes you think that you can do it introducing another layer of composition? Maybe you shall think that composition is a wrong tool in that case?
 

Regards,

Thierry




--
Best regards,
Igor Stasenko.
Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Thierry Goubier
In reply to this post by Igor Stasenko
Le 03/04/2016 19:12, Igor Stasenko a écrit :

>
>
> On 3 April 2016 at 19:48, Thierry Goubier <[hidden email]
> <mailto:[hidden email]>> wrote:
>
>     Le 03/04/2016 17:33, stepharo a écrit :
>
>         If you want to change clicking behaviour you need to override
>         one single
>         method.
>
>
>                      Everything you wrote with unreadable amount of
>             characters is
>                      for nothing.
>
>                  I see clearly point of Igor. And for me it feels very
>             logical.
>                  With such design you can lively change clipping area and
>                  interaction area for any morph (element) on screen.
>
>
>             In short, i see only two cases where indeed, morph requires
>             a nothing
>             of shapes to define:
>               - clipping region(s)
>               - ui interaction region(s)
>
>             but for drawing? nooooo... really? who cares what you draw
>             there?
>             draw anything, in any possible way you see fit.. compose,
>             decompose,
>             recombine, blend and mix.. that's the whole purpose of
>             drawing and be
>             artistic and be able to express yourself in any possible way
>             you want :)
>             Why nailing and formalizing things that are tend to be hardly
>             formalizable and more than that, unnecessary.
>             That's my main concern about current design.
>
>
>         I agree.
>         I do not see why people are forced to create a submorph just to
>         change
>         the rendering.
>         If you want to change it dynamically you can for example pass a
>         different shape.
>
>
>     I don't see the problem with subclassing a morph.
>
> Me neither. But do you confusing subclassing and submorph compositing?

Let me return you the question then: do you do a composition of
submorphs if you're trying to get a different drawOn:?

Oh, ok, that's true FastTable does it for the selection... changing
background color by encapsulating a row in another Morph with the right
background color.

>     The reverse: I feel like current Morphs are huge monsters of
>     configurability and parameter blocks and properties and intricated
>     code and thousands of methods so that one doesn't has to subclass...
>
> Agree, the Morph protocol is bloated. And i don't like it too.
> That is a result of lifting features and properties up in inheritance chain.
> And i can imagine how it happens over time:
> - we have a morph..
> - hurray!
> - can we have a morph with a border?
> - yes! Here BorderedMorph for you!
> - nice.. but can i use border in another subclass of Morph?
> - yes! Here borderStyle: property for you.. (and BorderedMorph is now
> useless)
>
> Or take a layout.. We could have , say, MorphWithLayout class. That
> introducing layouts. While other, simpler morph don't. Really, what
> layout you need in a morph that contains a plain rectangle fully
> covering its bounds?
> Or even 'having submorphs'. We could have MorphWithSubmorphs. Which
> could introduce submorphs concept.
>
> Separation of concerns. Good way to go. But if you need to have a morph
> that both has layout and border, then you are in trouble: you forced to
> do one of following:
>   - make own Morph subclass, duplicating features of both.. or make a
> composition of submorphs that will represent both features, or... lift
> both features to the top of inheritance chain, getting bloat as result.
> Most of the times, most of things are achiveable through composition..
> but some of them.. like drawing - apparently not.
> In any case i agree, that many features, that Morph proposing out of the
> box needs review and validation in terms, what if we isolate certain
> feature(s) in separate subclass and provide them via composition.

Yes, I do think you're right.

>     Simpler, "subclassable" morphs suits me a lot better.
>
>     Bloc looks like its taking some of the bad aspects of Morphic.
>
> One step at a time. You cannot fix all the problems of parent at once.
> The way how Bloc born, i think (i may be mistaken), it is a 'clean and
> lean' port of Morphic. But of course Morphic is huge monster, and
> porting such monster while rewriting its complex logic at the same time
> could be daunting hard.
> In any case, i think it is better. Let us hope, it will be even better.

I do hope. Certain points really require switching to Athens (sub-pixel
rendering of large fonts is extremely slow), and Bloc will be the
toolkit we'll have to live with.

Regards,

Thierry

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Henrik Nergaard

>Let me return you the question then: do you do a composition of submorphs if you're trying to get a different drawOn:?

>Oh, ok, that's true FastTable does it for the selection... changing background color by encapsulating a row in another Morph with the right background color.

Did, not anymore.

FTTableRowMorph>>#selectionColor:

Best regards,
Henrik

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Igor Stasenko
In reply to this post by Thierry Goubier


On 3 April 2016 at 20:51, Thierry Goubier <[hidden email]> wrote:
Le 03/04/2016 19:12, Igor Stasenko a écrit :


On 3 April 2016 at 19:48, Thierry Goubier <[hidden email]
<mailto:[hidden email]>> wrote:

    Le 03/04/2016 17:33, stepharo a écrit :

        If you want to change clicking behaviour you need to override
        one single
        method.


                     Everything you wrote with unreadable amount of
            characters is
                     for nothing.

                 I see clearly point of Igor. And for me it feels very
            logical.
                 With such design you can lively change clipping area and
                 interaction area for any morph (element) on screen.


            In short, i see only two cases where indeed, morph requires
            a nothing
            of shapes to define:
              - clipping region(s)
              - ui interaction region(s)

            but for drawing? nooooo... really? who cares what you draw
            there?
            draw anything, in any possible way you see fit.. compose,
            decompose,
            recombine, blend and mix.. that's the whole purpose of
            drawing and be
            artistic and be able to express yourself in any possible way
            you want :)
            Why nailing and formalizing things that are tend to be hardly
            formalizable and more than that, unnecessary.
            That's my main concern about current design.


        I agree.
        I do not see why people are forced to create a submorph just to
        change
        the rendering.
        If you want to change it dynamically you can for example pass a
        different shape.


    I don't see the problem with subclassing a morph.

Me neither. But do you confusing subclassing and submorph compositing?

Let me return you the question then: do you do a composition of submorphs if you're trying to get a different drawOn:?

Who, me? No. Maybe i was just misunderstood your reply.
Because what i was tried to demonstrate in previous post(s) that there's simply no easy way to expose all possible drawing operations via composition of morphs (or composition of any other kind of elements), unless, of course you will lift full feature set of Athens to the level of composition..
As result you will get a full feature set that Athens provides, plus extra complexity. 
Sounds like thing to do, no? :)
 
Oh, ok, that's true FastTable does it for the selection... changing background color by encapsulating a row in another Morph with the right background color.

Well, i don't know what is FastTable beast are.. so i cannot comment on this one.
 

    The reverse: I feel like current Morphs are huge monsters of
    configurability and parameter blocks and properties and intricated
    code and thousands of methods so that one doesn't has to subclass...

Agree, the Morph protocol is bloated. And i don't like it too.
That is a result of lifting features and properties up in inheritance chain.
And i can imagine how it happens over time:
- we have a morph..
- hurray!
- can we have a morph with a border?
- yes! Here BorderedMorph for you!
- nice.. but can i use border in another subclass of Morph?
- yes! Here borderStyle: property for you.. (and BorderedMorph is now
useless)

Or take a layout.. We could have , say, MorphWithLayout class. That
introducing layouts. While other, simpler morph don't. Really, what
layout you need in a morph that contains a plain rectangle fully
covering its bounds?
Or even 'having submorphs'. We could have MorphWithSubmorphs. Which
could introduce submorphs concept.

Separation of concerns. Good way to go. But if you need to have a morph
that both has layout and border, then you are in trouble: you forced to
do one of following:
  - make own Morph subclass, duplicating features of both.. or make a
composition of submorphs that will represent both features, or... lift
both features to the top of inheritance chain, getting bloat as result.
Most of the times, most of things are achiveable through composition..
but some of them.. like drawing - apparently not.
In any case i agree, that many features, that Morph proposing out of the
box needs review and validation in terms, what if we isolate certain
feature(s) in separate subclass and provide them via composition.

Yes, I do think you're right.

    Simpler, "subclassable" morphs suits me a lot better.

    Bloc looks like its taking some of the bad aspects of Morphic.

One step at a time. You cannot fix all the problems of parent at once.
The way how Bloc born, i think (i may be mistaken), it is a 'clean and
lean' port of Morphic. But of course Morphic is huge monster, and
porting such monster while rewriting its complex logic at the same time
could be daunting hard.
In any case, i think it is better. Let us hope, it will be even better.

I do hope. Certain points really require switching to Athens (sub-pixel rendering of large fonts is extremely slow), and Bloc will be the toolkit we'll have to live with.

Regards,

Thierry




--
Best regards,
Igor Stasenko.
Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Thierry Goubier
In reply to this post by Henrik Nergaard
Le 03/04/2016 20:00, Henrik Nergaard a écrit :

>
>> Let me return you the question then: do you do a composition of
>> submorphs if you're trying to get a different drawOn:?
>
>> Oh, ok, that's true FastTable does it for the selection... changing
>> background color by encapsulating a row in another Morph with the
>> right background color.
>
> Did, not anymore.
>
> FTTableRowMorph>>#selectionColor:

Had to check the following code to be sure:

                (highligtedRowIndexes includes: rowIndex) ifTrue: [
                        row selectionColor: (self owner colorForSelection:
primarySelectionIndex = rowIndex) ].

Was there a measurable inpact when changing that?

Because I have now three ways of doing this, and all of them have
trade-offs. For example the one above suppose that row items are a
specific kind of Morph, i.e. FTTableRowMorph; one could do without a
dedicated Morph subclass for rows and display the selection as a
transparent colored rectangle over the row; this is what I do.

Thierry

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

stepharo
In reply to this post by Aliaksei Syrel


Le 3/4/16 18:23, Aliaksei Syrel a écrit :
This means that any abstraction/wrapper around athens will fail.

What if we would remove drawingShape and by default leave drawOn: method to be empty. That way we would not put any constraints on rendering part. user just gets athens canvas and can do whatever she wants.

Instead we would have only clipping shape and event area shape.
What do you think? :)

I have the impression that this is a good solution.


Cheers,
Alex

On Sun, Apr 3, 2016 at 6:04 PM, Igor Stasenko <[hidden email]> wrote:


On 3 April 2016 at 17:58, Aliaksei Syrel <[hidden email]> wrote:
And you lost me here.. That is complete nonsense.. from any perspective.
Can i unsee this code, please? :)

If I would say that we have defaultShape method and it can be overridden as:

defaultShape
 ^ BlShape new
    fillPaint: (BlColorPaint new color: (Color yellow));
    path: BlRectanglePath new
would it make you happy?

Nope. (see bottom of reply why)
 
 .. to me it feels like: okay, what we need to do, to prevent overrides of our beloved default #drawOn: method.
You are wrong concerning preventing to override drawOn :)
Don't forget that there was a customer requirement concerning bloc:

Can we change how morph looks on fly? Can we create a rectangle morph and change it's shape from rectangle to circle? Because it can nicely show while presenting that Pharo is live system. I'm pretty sure Stef said it once ago.

Do you see how bloc story can nicely be told:
We have basic UI elements and each element has shape that can be easily changed live. Shape is defined by a path which can be filled or stroked using a paint. Complex elements can be created as composition of elements with basic shapes (rectangle, circle). 

Isn't it beautiful? :)

Nope. Because it would be beautiful, if your statements would be reflected in
reality and by reality.
In your example #defaultShape method, you simply isolating some behavior into a separate method. It does not changes anything.

You want to achieve to be able to change shapes on the fly. Good. A honourable goal. And welcoming. No objections here.

But can we achieve it without losing being able to change the color of shape on the fly. Please? :)
The way you introducing it goes straightly into conflict with: i want to be able to draw anything, the way i feel and like. 
You proposing a bad trade: oh yeah, you wanted to change shapes on the fly.. good.. but at cost of unable to draw anything else than simple rectangles in simple order.. 
Well.. i am not buying such trade. Can you sweeten a deal?

The point is, that shape is not the only thing you need to put into equation in order to get thing on the screen.. You also need paint. And that's the reason why you have  
fillPaint: (BlColorPaint new color: (Color yellow));

(lets put aside the hardcoding of color in unrelated place (defaultShape).. for the sake of example)
but does that fully covers all and any possible ways and needs of drawing?
Nope! Again not..
And voila, say welcome to composite "shapes" or "elements" or call it as you like it.
But does that fully covers all and any possible ways you can draw something with Athens?
Nope, it is not. Again. Sorry. You can achieve that only if you completely encode all possible operations and features provided by Athens using some kind of command pattern and put them in 'element' or 'compositeElement' or 'compositeOfCompositeElementsComposition' whatever.

For instance, how you going to encode AthensPaintMode into your elements? 
I guess you will offer to kill it with your 'it is not used so often' knife.

Can't you see that you basically creating a wrapper for all Athens feature set. 
I can tell you that you wasting effort: you cannot get anything extra by doing it. Except from extra complexity.
And for what? Something that already there and can be used out of the box.

If you don't like Athens API - go on, and change it. Make it better and more convenient to use. But encapsulating all possible combinations of all possible drawing operations? Good luck with that.


Cheers,
Alex

On Sun, Apr 3, 2016 at 3:37 PM, Igor Stasenko <[hidden email]> wrote:


On 3 April 2016 at 16:20, Igor Stasenko <[hidden email]> wrote:


On 3 April 2016 at 15:28, Glenn Cavarlé <[hidden email]> wrote:
Hi,

Aliaksei Syrel wrote
> However, in most UI of applications (in web, mobile) it is extremely rare
> that clipping or event handling areas differ from drawing one (visual one
> -
> one that user sees in the end).

It is the same for desktop UI (Qt, JavaFx,...).

I think the misunderstanding come from "shape", so let us forget BlShape and
concentrate on BlElement.

In fact, using Bloc now, If we want a Rectangle with an clickable inner
Circle, we have to defined 2 elements, the Rectangle one and the Circle one
(subclass of BlElement or using script style).
The CircleElement must be the child of the RectangleElement but we don't
have to override any method or to rewire CircleElement events back to its
parent, we just need to add an event listener to the CircleElement from
where we want.
It is the same with a Text in a Rectangle, we need a BlElement for the Text
and another for the Rectangle in order to compose them and to position the
Text in the Rectangle.

For me its like defining a CircleButton in a RectanglePanel with any other
ui libraries, i can do that by subclassing Panel or by using script style.
But i have to manipulate 2 elements and it makes sense for me.

Bloc does not provide user-friendly high-level abstractions at BlShape or
BlElement level like BlCircleShape or BlCircleElement.
I don't know if it is the right place to add them but it is clearly a point
of misunderstanding when people uses Bloc.
 
 
It seems to me that Bloc is not made to be used direclty as a graphical
framework but it is a librarie to build more user-friendly graphical
framework.
Shape, Path, ... are implementations stuff, most of users should not care
about that using a "framework".

Thanks for explanation.. 
Now i have a hard time understanding, what is the purpose of so-called 'element'. Element of what? What its role?
What its interaction between morphs and shapes, and what you see & feel on the screen?

>From your description, what i can tell is that it is completely unnecessary.
You have morphs to define hierarchy/composition.
And you can use shapes to define geometry for UI/clipping.
As for drawing - there's no need to put any constraints, you don't have to even mention that there are shapes involved. It is indeed, an implementation detail from that perspective, since you drawing things using Athens, and it uses shapes to define affected regions. But that completely orthogonal to what happens at UI level.
Thus, it is very surprising to me see following code snippet:


BlCell>>initialize
    super initialize.
    self
        shape:
            (BlShape new
                fillPaint: (BlColorPaint new color: (Color yellow));
                path: BlRectanglePath new);
        extent: self extent

because it is really seems like encapsulation of what you gonna draw.. 
and putting it into #initialize method in some form? 

And you lost me here.. That is complete nonsense.. from any perspective.
Can i unsee this code, please? :)

<acid mode on>
.. to me it feels like: okay, what we need to do, to prevent overrides of our beloved default #drawOn: method.

And you talking about 'sophistication' after that?
 
</acid mode off>

 
 
PS: @Alex, what are the planned refactoring? I'm lost in the new intentions
and in the roadmap of Bloc...
Regards,
Glenn.



-----
Glenn Cavarlé
--
View this message in context: http://forum.world.st/bloc-shape-size-tp4887929p4888039.html
Sent from the Pharo Smalltalk Developers mailing list archive at Nabble.com.




--
Best regards,
Igor Stasenko.



--
Best regards,
Igor Stasenko.




--
Best regards,
Igor Stasenko.


Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Henrik Nergaard
In reply to this post by Thierry Goubier
I changed it mostly because it was messing up the color when you did mouse-over (required to check the owner color to set it correctly when there was a selection, the code was ugly and with corner cases).

Encapsulating a morph with another morph just for a background color is kind of waste IMO. Causing unnecessary overhead for rendering/layout/eventHandling etc...

Mesurable? Don’t think I checked, but in the long run there is less allocations, less layout etc..
I would also argue that
------------------
                (highligtedRowIndexes includes: rowIndex) ifTrue: [
                        row selectionColor: (self owner colorForSelection:
primarySelectionIndex = rowIndex) ].
-----------------
Is better than
-----------------

                rowSubviews add: ((highligtedRowIndexes includes: rowIndex)
                        ifTrue: [
                                "IMPORTANT: I need to set owner to nil because otherwise it will trigger an
                                 invalidation of the owner when adding morph to selectionMorph, causing an
                                 infinite loop"
                                self
                                        toSelectionRow: (row privateOwner: nil)
                                        primary: primarySelectionIndex = rowIndex ]
                        ifFalse: [ row ]) ].
-----------------------

Selection could be and drawn by the container, but then again you would need much more code and special logic (updating the damageRecorder with correct rectangles when selection changes for example) than to just extend and specialize one morph to be a row.

I would much rather prefer one specialized morph doing its thing, than encapsulate it.

Best regards,
Henrik

-----Original Message-----
From: Pharo-dev [mailto:[hidden email]] On Behalf Of Thierry Goubier
Sent: Sunday, April 3, 2016 8:58 PM
To: Pharo Development List <[hidden email]>
Subject: Re: [Pharo-dev] [bloc] shape size?

Le 03/04/2016 20:00, Henrik Nergaard a écrit :

>
>> Let me return you the question then: do you do a composition of
>> submorphs if you're trying to get a different drawOn:?
>
>> Oh, ok, that's true FastTable does it for the selection... changing
>> background color by encapsulating a row in another Morph with the
>> right background color.
>
> Did, not anymore.
>
> FTTableRowMorph>>#selectionColor:

Had to check the following code to be sure:

                (highligtedRowIndexes includes: rowIndex) ifTrue: [
                        row selectionColor: (self owner colorForSelection:
primarySelectionIndex = rowIndex) ].

Was there a measurable inpact when changing that?

Because I have now three ways of doing this, and all of them have trade-offs. For example the one above suppose that row items are a specific kind of Morph, i.e. FTTableRowMorph; one could do without a dedicated Morph subclass for rows and display the selection as a transparent colored rectangle over the row; this is what I do.

Thierry

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Thierry Goubier
In reply to this post by Igor Stasenko
Le 03/04/2016 20:01, Igor Stasenko a écrit :

>
>
> On 3 April 2016 at 20:51, Thierry Goubier <[hidden email]
> <mailto:[hidden email]>> wrote:
>
>     Le 03/04/2016 19:12, Igor Stasenko a écrit :
>
>
>
>         On 3 April 2016 at 19:48, Thierry Goubier
>         <[hidden email] <mailto:[hidden email]>
>         <mailto:[hidden email]
>         <mailto:[hidden email]>>> wrote:
>
>              Le 03/04/2016 17:33, stepharo a écrit :
>
>                  If you want to change clicking behaviour you need to
>         override
>                  one single
>                  method.
>
>
>                               Everything you wrote with unreadable amount of
>                      characters is
>                               for nothing.
>
>                           I see clearly point of Igor. And for me it
>         feels very
>                      logical.
>                           With such design you can lively change
>         clipping area and
>                           interaction area for any morph (element) on
>         screen.
>
>
>                      In short, i see only two cases where indeed, morph
>         requires
>                      a nothing
>                      of shapes to define:
>                        - clipping region(s)
>                        - ui interaction region(s)
>
>                      but for drawing? nooooo... really? who cares what
>         you draw
>                      there?
>                      draw anything, in any possible way you see fit..
>         compose,
>                      decompose,
>                      recombine, blend and mix.. that's the whole purpose of
>                      drawing and be
>                      artistic and be able to express yourself in any
>         possible way
>                      you want :)
>                      Why nailing and formalizing things that are tend to
>         be hardly
>                      formalizable and more than that, unnecessary.
>                      That's my main concern about current design.
>
>
>                  I agree.
>                  I do not see why people are forced to create a submorph
>         just to
>                  change
>                  the rendering.
>                  If you want to change it dynamically you can for
>         example pass a
>                  different shape.
>
>
>              I don't see the problem with subclassing a morph.
>
>         Me neither. But do you confusing subclassing and submorph
>         compositing?
>
>
>     Let me return you the question then: do you do a composition of
>     submorphs if you're trying to get a different drawOn:?
>
> Who, me? No. Maybe i was just misunderstood your reply.
> Because what i was tried to demonstrate in previous post(s) that there's
> simply no easy way to expose all possible drawing operations via
> composition of morphs (or composition of any other kind of elements),
> unless, of course you will lift full feature set of Athens to the level
> of composition..
> As result you will get a full feature set that Athens provides, plus
> extra complexity.
> Sounds like thing to do, no? :)

Agreed :)

>     Oh, ok, that's true FastTable does it for the selection... changing
>     background color by encapsulating a row in another Morph with the
>     right background color.
>
> Well, i don't know what is FastTable beast are.. so i cannot comment on
> this one.

I think FastTable is something you should have a look at. Esteban did
something really interesting there.

In FT, Submorphs are only created when they are about to be displayed:
Pharo can easily create hundreds of morphs on every redraw cycle. So FT
performance is O(k) where k is the number of rows to display on screen
(typical k is ~25), and is O(1) regarding the length of the list
(almost: there is a point, for very large tree-like structures, where
just iterating over the structure becomes the main performance
limitation: see FTTree).

A FTTableContainerMorph recreates all its submorphs on every drawOn:.
I've played with different variants (do not recreate all submorphs, for
example) but you don't see any performance difference (on the time
needed for a drawOn:).

Regards,

Thierry

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Henrik Nergaard
>A FTTableContainerMorph recreates all its submorphs on every drawOn:.
Not correct.

Submorphs are only recreated when the view of the list has changed #canRefreshValues, ie if the variable "needsRefreshExposedRows" is set to true.  If this is false nothing will happen in #drawOn:

If changes is necessary the drawOn: will recreate submorphs for the current view (showIndex) and set the "needsRefreshedExposedRows" to false signalling that it is correctly laid out.


Best regards,
Henrik


-----Original Message-----
From: Pharo-dev [mailto:[hidden email]] On Behalf Of Thierry Goubier
Sent: Sunday, April 3, 2016 9:32 PM
To: Pharo Development List <[hidden email]>
Subject: Re: [Pharo-dev] [bloc] shape size?

I think FastTable is something you should have a look at. Esteban did something really interesting there.

In FT, Submorphs are only created when they are about to be displayed:
Pharo can easily create hundreds of morphs on every redraw cycle. So FT performance is O(k) where k is the number of rows to display on screen (typical k is ~25), and is O(1) regarding the length of the list
(almost: there is a point, for very large tree-like structures, where just iterating over the structure becomes the main performance
limitation: see FTTree).

A FTTableContainerMorph recreates all its submorphs on every drawOn:.
I've played with different variants (do not recreate all submorphs, for
example) but you don't see any performance difference (on the time needed for a drawOn:).

Regards,

Thierry

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Thierry Goubier
In reply to this post by Henrik Nergaard
Hi Henrik,

Le 03/04/2016 21:32, Henrik Nergaard a écrit :
> I changed it mostly because it was messing up the color when you did
> mouse-over (required to check the owner color to set it correctly when
> there was a selection, the code was ugly and with corner cases).

Ok.

> Encapsulating a morph with another morph just for a background color
> is kind of waste IMO. Causing unnecessary overhead for
> rendering/layout/eventHandling etc...

Rendering maybe a bit. Layout, maybe a bit. Event handling? Oh well, row
morphs contents are already a tree of morphs at least 3 deep, what will
be the effect of one more doing nothing?

> Mesurable? Don’t think I checked, but in the long run there is less allocations, less layout etc..

I guess that, given how FT works, it is hidden in the number of Morph
creation per drawOn: :)

> I would also argue that
> ------------------
> (highligtedRowIndexes includes: rowIndex) ifTrue: [
> row selectionColor: (self owner colorForSelection:
> primarySelectionIndex = rowIndex) ].
> -----------------
> Is better than
> -----------------
>
> rowSubviews add: ((highligtedRowIndexes includes: rowIndex)
> ifTrue: [
> "IMPORTANT: I need to set owner to nil because otherwise it will trigger an
> invalidation of the owner when adding morph to selectionMorph, causing an
> infinite loop"
> self
> toSelectionRow: (row privateOwner: nil)
> primary: primarySelectionIndex = rowIndex ]
> ifFalse: [ row ]) ].
> -----------------------

I like the game with #privateOwner: in the FT code. Tells you a lot
about ownership in Morphic :)

At the same time, your new code isn't very clear. It is written just as
the setting of a theme property where in fact it is setting the row as
selected.

> Selection could be and drawn by the container, but then again you
> would need much more code and special logic (updating the damageRecorder
> with correct rectangles when selection changes for example) than to just
> extend and specialize one morph to be a row.

I'm doing the selection draw by container, and, honestly, there is none
of the complexity you describe. Selection is a model operation anyway,
so it usually triggers a redraw (because selection may move you
elsewhere, if the model so chooses); if you have some caching in place
(that FT hasn't), you gain a bit upon redraw, but nothing noticeable.

There is another reason for moving it into the container, but that
reason is not public.

> I would much rather prefer one specialized morph doing its thing, than encapsulate it.

I think the FTTableRowMorph has other duties anyway, so giving him that
additional role is fine.

Regards,

Thierry

> Best regards,
> Henrik
>
> -----Original Message-----
> From: Pharo-dev [mailto:[hidden email]] On Behalf Of Thierry Goubier
> Sent: Sunday, April 3, 2016 8:58 PM
> To: Pharo Development List <[hidden email]>
> Subject: Re: [Pharo-dev] [bloc] shape size?
>
> Le 03/04/2016 20:00, Henrik Nergaard a écrit :
>>
>>> Let me return you the question then: do you do a composition of
>>> submorphs if you're trying to get a different drawOn:?
>>
>>> Oh, ok, that's true FastTable does it for the selection... changing
>>> background color by encapsulating a row in another Morph with the
>>> right background color.
>>
>> Did, not anymore.
>>
>> FTTableRowMorph>>#selectionColor:
>
> Had to check the following code to be sure:
>
> (highligtedRowIndexes includes: rowIndex) ifTrue: [
> row selectionColor: (self owner colorForSelection:
> primarySelectionIndex = rowIndex) ].
>
> Was there a measurable inpact when changing that?
>
> Because I have now three ways of doing this, and all of them have trade-offs. For example the one above suppose that row items are a specific kind of Morph, i.e. FTTableRowMorph; one could do without a dedicated Morph subclass for rows and display the selection as a transparent colored rectangle over the row; this is what I do.
>
> Thierry
>


Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Igor Stasenko
In reply to this post by Thierry Goubier


On 3 April 2016 at 22:32, Thierry Goubier <[hidden email]> wrote:
Le 03/04/2016 20:01, Igor Stasenko a écrit :


On 3 April 2016 at 20:51, Thierry Goubier <[hidden email]
<mailto:[hidden email]>> wrote:

    Le 03/04/2016 19:12, Igor Stasenko a écrit :



        On 3 April 2016 at 19:48, Thierry Goubier
        <[hidden email] <mailto:[hidden email]>
        <mailto:[hidden email]

        <mailto:[hidden email]>>> wrote:

             Le 03/04/2016 17:33, stepharo a écrit :

                 If you want to change clicking behaviour you need to
        override
                 one single
                 method.


                              Everything you wrote with unreadable amount of
                     characters is
                              for nothing.

                          I see clearly point of Igor. And for me it
        feels very
                     logical.
                          With such design you can lively change
        clipping area and
                          interaction area for any morph (element) on
        screen.


                     In short, i see only two cases where indeed, morph
        requires
                     a nothing
                     of shapes to define:
                       - clipping region(s)
                       - ui interaction region(s)

                     but for drawing? nooooo... really? who cares what
        you draw
                     there?
                     draw anything, in any possible way you see fit..
        compose,
                     decompose,
                     recombine, blend and mix.. that's the whole purpose of
                     drawing and be
                     artistic and be able to express yourself in any
        possible way
                     you want :)
                     Why nailing and formalizing things that are tend to
        be hardly
                     formalizable and more than that, unnecessary.
                     That's my main concern about current design.


                 I agree.
                 I do not see why people are forced to create a submorph
        just to
                 change
                 the rendering.
                 If you want to change it dynamically you can for
        example pass a
                 different shape.


             I don't see the problem with subclassing a morph.

        Me neither. But do you confusing subclassing and submorph
        compositing?


    Let me return you the question then: do you do a composition of
    submorphs if you're trying to get a different drawOn:?

Who, me? No. Maybe i was just misunderstood your reply.
Because what i was tried to demonstrate in previous post(s) that there's
simply no easy way to expose all possible drawing operations via
composition of morphs (or composition of any other kind of elements),
unless, of course you will lift full feature set of Athens to the level
of composition..
As result you will get a full feature set that Athens provides, plus
extra complexity.
Sounds like thing to do, no? :)

Agreed :)

    Oh, ok, that's true FastTable does it for the selection... changing
    background color by encapsulating a row in another Morph with the
    right background color.

Well, i don't know what is FastTable beast are.. so i cannot comment on
this one.

I think FastTable is something you should have a look at. Esteban did something really interesting there.

In FT, Submorphs are only created when they are about to be displayed: Pharo can easily create hundreds of morphs on every redraw cycle. So FT performance is O(k) where k is the number of rows to display on screen (typical k is ~25), and is O(1) regarding the length of the list (almost: there is a point, for very large tree-like structures, where just iterating over the structure becomes the main performance limitation: see FTTree).

Sounds like right way to do it. There's no point to keep million UI elements for million items in list, since you never render them all at once on the screen. So, practical approach is to create as many UI elements as fits on the screen, but not as many you have in list.
 
A FTTableContainerMorph recreates all its submorphs on every drawOn:. I've played with different variants (do not recreate all submorphs, for example) but you don't see any performance difference (on the time needed for a drawOn:).

Yeah, i did similar thing in TxText - also create morph(s) only for part of text which is currently displayed.. and basically it is same idea for TxText itself: it calculates layout only for a portion of text, the portion that currently displayed, but never for whole text, which can be megabytes long.
Thus, it guarantees that overall performance are bound to the area, covered by UI control that displays the text, but not to text size.

 
Regards,

Thierry




--
Best regards,
Igor Stasenko.
Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Thierry Goubier
In reply to this post by Henrik Nergaard
Le 03/04/2016 21:51, Henrik Nergaard a écrit :
>> A FTTableContainerMorph recreates all its submorphs on every
>> drawOn:.
> Not correct.

Ok. I stand corrected. This is why it is done in #drawOn: and not
#drawSubmorphsOn:

> Submorphs are only recreated when the view of the list has changed
> #canRefreshValues, ie if the variable "needsRefreshExposedRows" is
> set to true.  If this is false nothing will happen in #drawOn:
>
> If changes is necessary the drawOn: will recreate submorphs for the
> current view (showIndex) and set the "needsRefreshedExposedRows" to
> false signalling that it is correctly laid out.

What is interesting, still, is that submorphs rebuilding (deleting and
recreating them) happens during a #drawOn: call, and that it is fast
enough not to register on the time needed for a world redraw.

And so I still think it is interesting for Igor to have a look at FT :)

Regards,

Thierry

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Uko2
In reply to this post by Igor Stasenko

On 03 Apr 2016, at 21:58, Igor Stasenko <[hidden email]> wrote:



On 3 April 2016 at 22:32, Thierry Goubier <[hidden email]> wrote:
Le 03/04/2016 20:01, Igor Stasenko a écrit :


On 3 April 2016 at 20:51, Thierry Goubier <[hidden email]
<mailto:[hidden email]>> wrote:

    Le 03/04/2016 19:12, Igor Stasenko a écrit :



        On 3 April 2016 at 19:48, Thierry Goubier
        <[hidden email] <mailto:[hidden email]>
        <mailto:[hidden email]

        <mailto:[hidden email]>>> wrote:

             Le 03/04/2016 17:33, stepharo a écrit :

                 If you want to change clicking behaviour you need to
        override
                 one single
                 method.


                              Everything you wrote with unreadable amount of
                     characters is
                              for nothing.

                          I see clearly point of Igor. And for me it
        feels very
                     logical.
                          With such design you can lively change
        clipping area and
                          interaction area for any morph (element) on
        screen.


                     In short, i see only two cases where indeed, morph
        requires
                     a nothing
                     of shapes to define:
                       - clipping region(s)
                       - ui interaction region(s)

                     but for drawing? nooooo... really? who cares what
        you draw
                     there?
                     draw anything, in any possible way you see fit..
        compose,
                     decompose,
                     recombine, blend and mix.. that's the whole purpose of
                     drawing and be
                     artistic and be able to express yourself in any
        possible way
                     you want :)
                     Why nailing and formalizing things that are tend to
        be hardly
                     formalizable and more than that, unnecessary.
                     That's my main concern about current design.


                 I agree.
                 I do not see why people are forced to create a submorph
        just to
                 change
                 the rendering.
                 If you want to change it dynamically you can for
        example pass a
                 different shape.


             I don't see the problem with subclassing a morph.

        Me neither. But do you confusing subclassing and submorph
        compositing?


    Let me return you the question then: do you do a composition of
    submorphs if you're trying to get a different drawOn:?

Who, me? No. Maybe i was just misunderstood your reply.
Because what i was tried to demonstrate in previous post(s) that there's
simply no easy way to expose all possible drawing operations via
composition of morphs (or composition of any other kind of elements),
unless, of course you will lift full feature set of Athens to the level
of composition..
As result you will get a full feature set that Athens provides, plus
extra complexity.
Sounds like thing to do, no? :)

Agreed :)

    Oh, ok, that's true FastTable does it for the selection... changing
    background color by encapsulating a row in another Morph with the
    right background color.

Well, i don't know what is FastTable beast are.. so i cannot comment on
this one.

I think FastTable is something you should have a look at. Esteban did something really interesting there.

In FT, Submorphs are only created when they are about to be displayed: Pharo can easily create hundreds of morphs on every redraw cycle. So FT performance is O(k) where k is the number of rows to display on screen (typical k is ~25), and is O(1) regarding the length of the list (almost: there is a point, for very large tree-like structures, where just iterating over the structure becomes the main performance limitation: see FTTree).

Sounds like right way to do it. There's no point to keep million UI elements for million items in list, since you never render them all at once on the screen. So, practical approach is to create as many UI elements as fits on the screen, but not as many you have in list.

I think that Cocoa list does that. When a list item goes out of the screen it’s sent to a pool, and when a new one has to be displayed they take any one from that pool and re-initialize.

 
A FTTableContainerMorph recreates all its submorphs on every drawOn:. I've played with different variants (do not recreate all submorphs, for example) but you don't see any performance difference (on the time needed for a drawOn:).

Yeah, i did similar thing in TxText - also create morph(s) only for part of text which is currently displayed.. and basically it is same idea for TxText itself: it calculates layout only for a portion of text, the portion that currently displayed, but never for whole text, which can be megabytes long.
Thus, it guarantees that overall performance are bound to the area, covered by UI control that displays the text, but not to text size.

 
Regards,

Thierry




-- 
Best regards,
Igor Stasenko.

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Igor Stasenko
In reply to this post by Thierry Goubier


On 3 April 2016 at 23:00, Thierry Goubier <[hidden email]> wrote:
Le 03/04/2016 21:51, Henrik Nergaard a écrit :
A FTTableContainerMorph recreates all its submorphs on every
drawOn:.
Not correct.

Ok. I stand corrected. This is why it is done in #drawOn: and not #drawSubmorphsOn:

Submorphs are only recreated when the view of the list has changed
#canRefreshValues, ie if the variable "needsRefreshExposedRows" is
set to true.  If this is false nothing will happen in #drawOn:

If changes is necessary the drawOn: will recreate submorphs for the
current view (showIndex) and set the "needsRefreshedExposedRows" to
false signalling that it is correctly laid out.

What is interesting, still, is that submorphs rebuilding (deleting and recreating them) happens during a #drawOn: call, and that it is fast enough not to register on the time needed for a world redraw.

And so I still think it is interesting for Igor to have a look at FT :)

Only for review purpose, i guess. From what you described, as i wrote in previous post this is not new to me. I think i seen some kind of morph(s) that was using same technique in the past. it may be different in details, of course, but overall idea was same: create and use as many UI elements, as many fits on the screen, not as many items in the list(s)
 
Regards,

Thierry




--
Best regards,
Igor Stasenko.
Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Thierry Goubier
In reply to this post by Igor Stasenko
Le 03/04/2016 21:58, Igor Stasenko a écrit :

>
>
> On 3 April 2016 at 22:32, Thierry Goubier <[hidden email]
> <mailto:[hidden email]>> wrote:
>
>     Le 03/04/2016 20:01, Igor Stasenko a écrit :
>
>
>
>         On 3 April 2016 at 20:51, Thierry Goubier
>         <[hidden email] <mailto:[hidden email]>
>         <mailto:[hidden email]
>         <mailto:[hidden email]>>> wrote:
>
>              Le 03/04/2016 19:12, Igor Stasenko a écrit :
>
>
>
>                  On 3 April 2016 at 19:48, Thierry Goubier
>                  <[hidden email]
>         <mailto:[hidden email]>
>         <mailto:[hidden email]
>         <mailto:[hidden email]>>
>                  <mailto:[hidden email]
>         <mailto:[hidden email]>
>
>                  <mailto:[hidden email]
>         <mailto:[hidden email]>>>> wrote:
>
>                       Le 03/04/2016 17:33, stepharo a écrit :
>
>                           If you want to change clicking behaviour you
>         need to
>                  override
>                           one single
>                           method.
>
>
>                                        Everything you wrote with
>         unreadable amount of
>                               characters is
>                                        for nothing.
>
>                                    I see clearly point of Igor. And for
>         me it
>                  feels very
>                               logical.
>                                    With such design you can lively change
>                  clipping area and
>                                    interaction area for any morph
>         (element) on
>                  screen.
>
>
>                               In short, i see only two cases where
>         indeed, morph
>                  requires
>                               a nothing
>                               of shapes to define:
>                                 - clipping region(s)
>                                 - ui interaction region(s)
>
>                               but for drawing? nooooo... really? who
>         cares what
>                  you draw
>                               there?
>                               draw anything, in any possible way you see
>         fit..
>                  compose,
>                               decompose,
>                               recombine, blend and mix.. that's the
>         whole purpose of
>                               drawing and be
>                               artistic and be able to express yourself
>         in any
>                  possible way
>                               you want :)
>                               Why nailing and formalizing things that
>         are tend to
>                  be hardly
>                               formalizable and more than that, unnecessary.
>                               That's my main concern about current design.
>
>
>                           I agree.
>                           I do not see why people are forced to create a
>         submorph
>                  just to
>                           change
>                           the rendering.
>                           If you want to change it dynamically you can for
>                  example pass a
>                           different shape.
>
>
>                       I don't see the problem with subclassing a morph.
>
>                  Me neither. But do you confusing subclassing and submorph
>                  compositing?
>
>
>              Let me return you the question then: do you do a composition of
>              submorphs if you're trying to get a different drawOn:?
>
>         Who, me? No. Maybe i was just misunderstood your reply.
>         Because what i was tried to demonstrate in previous post(s) that
>         there's
>         simply no easy way to expose all possible drawing operations via
>         composition of morphs (or composition of any other kind of
>         elements),
>         unless, of course you will lift full feature set of Athens to
>         the level
>         of composition..
>         As result you will get a full feature set that Athens provides, plus
>         extra complexity.
>         Sounds like thing to do, no? :)
>
>
>     Agreed :)
>
>              Oh, ok, that's true FastTable does it for the selection...
>         changing
>              background color by encapsulating a row in another Morph
>         with the
>              right background color.
>
>         Well, i don't know what is FastTable beast are.. so i cannot
>         comment on
>         this one.
>
>
>     I think FastTable is something you should have a look at. Esteban
>     did something really interesting there.
>
>     In FT, Submorphs are only created when they are about to be
>     displayed: Pharo can easily create hundreds of morphs on every
>     redraw cycle. So FT performance is O(k) where k is the number of
>     rows to display on screen (typical k is ~25), and is O(1) regarding
>     the length of the list (almost: there is a point, for very large
>     tree-like structures, where just iterating over the structure
>     becomes the main performance limitation: see FTTree).
>
> Sounds like right way to do it. There's no point to keep million UI
> elements for million items in list, since you never render them all at
> once on the screen. So, practical approach is to create as many UI
> elements as fits on the screen, but not as many you have in list.
>
>     A FTTableContainerMorph recreates all its submorphs on every
>     drawOn:. I've played with different variants (do not recreate all
>     submorphs, for example) but you don't see any performance difference
>     (on the time needed for a drawOn:).

Well, as Henrik pointed out, not everytime ;)

> Yeah, i did similar thing in TxText - also create morph(s) only for part
> of text which is currently displayed.. and basically it is same idea for
> TxText itself: it calculates layout only for a portion of text, the
> portion that currently displayed, but never for whole text, which can be
> megabytes long.
> Thus, it guarantees that overall performance are bound to the area,
> covered by UI control that displays the text, but not to text size.

I'm interested to know how you handle scrolling then: how do you define
the step, the length and the position: relative to the number of
characters displayed / start character of the current UI / and knowing
the number of characters in the whole text, so that you are independent
of the layout?

Regards,

Thierry

Reply | Threaded
Open this post in threaded view
|

Re: [bloc] shape size?

Thierry Goubier
In reply to this post by Igor Stasenko
Le 03/04/2016 22:26, Igor Stasenko a écrit :

>
>
> On 3 April 2016 at 23:00, Thierry Goubier <[hidden email]
> <mailto:[hidden email]>> wrote:
>
>     Le 03/04/2016 21:51, Henrik Nergaard a écrit :
>
>             A FTTableContainerMorph recreates all its submorphs on every
>             drawOn:.
>
>         Not correct.
>
>
>     Ok. I stand corrected. This is why it is done in #drawOn: and not
>     #drawSubmorphsOn:
>
>         Submorphs are only recreated when the view of the list has changed
>         #canRefreshValues, ie if the variable "needsRefreshExposedRows" is
>         set to true.  If this is false nothing will happen in #drawOn:
>
>         If changes is necessary the drawOn: will recreate submorphs for the
>         current view (showIndex) and set the "needsRefreshedExposedRows" to
>         false signalling that it is correctly laid out.
>
>
>     What is interesting, still, is that submorphs rebuilding (deleting
>     and recreating them) happens during a #drawOn: call, and that it is
>     fast enough not to register on the time needed for a world redraw.
>
>     And so I still think it is interesting for Igor to have a look at FT :)
>
> Only for review purpose, i guess. From what you described, as i wrote in
> previous post this is not new to me. I think i seen some kind of
> morph(s) that was using same technique in the past. it may be different
> in details, of course, but overall idea was same: create and use as many
> UI elements, as many fits on the screen, not as many items in the list(s)

Yes, probably.

Regards,

Thierry

1234