Open qtxie opened 4 years ago
I'll share some of my thoughts here.
The ScrollView is a content container, it has a horizontal Scroller and a vertical Scroller. It implements the interaction details for a scrollable face. The user just need to populate it with sub faces. The scrollers will automatically show or hide according to the size of the bounding box of the sub faces in the ScrollView.
I actually have an imitation of it here. Imitation has a problem though: it has to attach reactions to all child faces, watch if those faces go out of pane (maybe into another scrollpanel). I.e. a lot of useless bookkeeping.
I think we do not need a separate ScrollView style. Each panel should be scrollable like this if it has a 'scrollable flag.
I also think such panel should react to wheel and pan events, scrolling itself accordingly, without any effort from the user (unless such event is captured by inner faces). Pan event will provide the scroll amount. How much to scroll (vertically) using the mouse wheel - should be controlled by the OS setting.
I would also expect it to react to clicks on the wheel (mbutton3) - like most programs do today - providing an autoscroll feature, either automatically or controlled by some flag. It should be able to scroll in both vertical and horizontal direction this way (depending on visible scrollbars).
It should provide an on-scroll
event that is triggered after it has moved it's viewport.
It should also provide a way to do reverse task: programmatically set it's viewport to some location (e.g. to the offset of some face), automatically adjusting the scrollers (on show
).
These two things should not cause event cascades (like on-scroll
modifies the scrollers -> this calls on-scroll
again).
If there will be an easy way to do it, I'd like to be able to choose the side for vertical scrollbar: right (default) or left (for left-handed or right-to-left writing users). Since even Windows still doesn't have any builtin setting to control that, it's not ultra important.
Another problem of my imitation is that scroller faces have to be exposed in the pane, and in order to always stay above the child faces I have to watch the pane constantly and move scrollers to the tail of it if e.g. one adds some other faces to the pane.
Then there's a problem of 2 scrollers: what to with the point where they intersect? It looks awkward if panel content pops out behind the scrollers: And I can accidentally click something I don't want to! Native apps put either an opaque box of panel color there, or a corner that may do nothing or resize the window when you drag it:
TBD: should we use face! or a special scroller! object?
I think standalone scroller must be a face. For the embedded one, let's count:
type
- always read-onlyoffset
/size
/visible?
- those should always be automatically set, but we may provide them for reading (how else one will know what part of the view is obscured by scrollbars?)text
/image
/color
/pane
/font
/para
- not supportedrate
/menu
- we don't have to support it for embedded scrollers(?)flags
- could have contained the direction (v/h)enabled?
- should be supported I thinkactors
- probably can be used for some customization, e.g. middle/right-clicks, shift/ctrl+clicks... etcdraw
- could be used to override embedded scrollers look with something custom, but needs testing if it won't cause flickerdata
may be used for position
scrollable
should become a VID keyword, not require messing with flags
. Also should be supported by rich-text
and window
and future table
. If we can, we should allow manipulating area
and text-list
scrollers using the same embedded interface.
One more thought. Though in most cases scrollers' offsets and sizes should be set automatically, there are still cases where they shouldn't be: In this table there are pinned columns and rows, and only the unpinned area is scrollable. I can also imagine rows pinned at the bottom (e.g. summary), so there must be some way to manually control the scrollers geometry. So to support this kind of control one would need to:
I am not sure that this extended model should be supported in a scrollview
. It's more like a thing a base
with embedded scrollbars should do. Just leaving it here for consideration.
There are two elements that enable scrolling in Red/View:
ScrollView
andScroller
.ScrollView
The ScrollView is a content container, it has a horizontal Scroller and a vertical Scroller. It implements the interaction details for a scrollable face. The user just need to populate it with sub faces. The scrollers will automatically show or hide according to the size of the bounding box of the sub faces in the ScrollView.
For example, builds a ListView by using ScrollView.
Scroller
There are two types of scroller:
Standalone Scroller
andEmbeded Scroller
.scroller!: object [ position: none ;-- knob position page-size: none ;-- page size min-size: 1 ;-- minimum value max-size: none ;-- maximum value visible?: yes vertical?: yes ;-- read only. YES: vertical NO: horizontal parent: none ]
view [b: base 300x300 do [b/flags: [scrollable]]]