#------------------------------------------------------------------------------
# Copyright (c) 2013, Nucleic Development Team.
#
# Distributed under the terms of the Modified BSD License.
#
# The full license is in the file COPYING.txt, distributed with this software.
#------------------------------------------------------------------------------
""" An example of the `FlowArea` widget.
A `FlowArea` is a very powerful tool for creating a flowing layout of
widgets. A `FlowArea` accepts an arbitrary number of `FlowItem` children,
each of which holds a `Container` as its content. The layout of these
`FlowItem` children is controlled by the `FlowArea` attributes:
`direction`
This is an enum controlling how the items are arranged in the
area. Allowable values are 'left_to_right', 'right_to_left',
'top_to_bottom', and 'bottom_to_top'; and indicate the direction
in which items will be added to the area. When the layout space
in a given direction is exhausted, the layout will wrap around
to the next line. With horizontal directions, lines are stacked
top to bottom. With vertical directions, lines are stacked
left to right.
`align`
This is an enum controlling how a layout line is aligned within
the layout space. If there is any space leftover after laying
out a given line of widgets, that space is distributed according
to the value of this enum. Allowable values are 'leading',
'trailing', 'center', and 'justify'.
`horizontal_spacing`
This is an int specifying how much horizontal space to place
between items or lines in the layout.
`vertical_spacing`
This is an int specifying how much vertical space to place
between items or lines in the layout.
`margins`
This is a Box of ints specifying how much margin to place
on the outside of the layout.
Each `FlowItem` used in the layout can further customize the behavior:
`preferred_size`
This is a Size specifying the desired layout size for the item.
This size will be used whenever possible, but will not override
the minimum or maximum size of the item. If set to (-1, -1)
(the default), then the size hint for the item will be used.
`align`
This is an enum which controls the orthogonal alignment of the
item. When an item has neighbors which are larger than itself
in the orhthongonal direction, this value controls how the item
aligns within that additional space. The valid values area
'leading', 'trailing', and 'center'.
`stretch`
This is an int which controls the amount that the widget should
expand to take up additional space in the layout direction. The
default is 0 and means that the widget will not expand. When the
value is greater than zero, the value is weighted against the
stretch factors of the other items in the same line to determine
the amount of space given to the item.
`ortho_stretch`
This is an int which controls the amount that the widget should
expand to take up additional space orthogonal to the layout
direction. The default is 0 and means that the widget will not
expand. If no item in a given line can expand in the ortho
direction, then the line will not expand. Otherwise, the stretch
factor for a line is equivalent to the maximum of the ortho
stretch factors for all items in the line. The extra orthogonal
space is then proportioned to the lines weighted on this stretch
factor.
The code below creates a flow area populated with several initial flow
items. Items can be added and removed, and each individual item is
configurable. There is a single item which cannot be removed, and which
controls the parameters for the entire area.
<< autodoc-me >>
"""
from enaml.core.api import Include
from enaml.widgets.api import (
FlowArea, FlowItem, Window, Form, Label, Field, SpinBox, ComboBox,
Container, Html, GroupBox, Slider, PushButton,
)
enamldef Item(FlowItem):
align << align_box.selected_item
stretch << flow_spin.value
ortho_stretch << ortho_spin.value
preferred_size << (pref_width.value, pref_height.value)
GroupBox:
Form:
padding = 0
Label:
text = 'Preferred Width'
SpinBox: pref_width:
minimum = -1
maximum = 800
value = -1
Label:
text = 'Preferred Height'
SpinBox: pref_height:
minimum = -1
maximum = 800
value = -1
Label:
text = 'Flow Stretch'
SpinBox: flow_spin:
minimum = 0
maximum = 100
value = 0
Label:
text = 'Ortho Stretch'
SpinBox: ortho_spin:
minimum = 0
maximum = 100
value = 0
Label:
text = 'Ortho Align'
ComboBox: align_box:
items = ['leading', 'center', 'trailing']
index = 0
Html:
resist_height = 'weak'
source = '<center>Hello World</center>'
enamldef AreaControls(GroupBox):
attr area: FlowArea
event add_item
event remove_item
title = 'Area Controls'
Label:
text =('Add new items to see how the flow area works.\n'
'You can also tweak the flow parameters')
PushButton:
text = 'Add Item'
clicked :: add_item()
PushButton:
text = 'Remove Item'
clicked :: remove_item()
Form:
padding = 0
Label:
text = 'Horizontal Spacing'
Slider:
minimum = 0
maximum = 150
value := area.horizontal_spacing
Label:
text = 'Vertical Spacing'
Slider:
minimum = 0
maximum = 150
value := area.vertical_spacing
Label:
text = 'Direction'
ComboBox:
items = [
'left_to_right', 'right_to_left',
'top_to_bottom', 'bottom_to_top',
]
index = items.index(area.direction)
selected_item >> area.direction
Label:
text = 'Align'
ComboBox:
items = ['leading', 'center', 'justify', 'trailing']
index = items.index(area.align)
selected_item >> area.align
enamldef Main(Window):
initial_size = (800,800)
Container:
FlowArea: flow_area:
FlowItem:
AreaControls:
area = flow_area
add_item ::
inc.objects.append(Item())
remove_item ::
if inc.objects:
inc.objects.pop()
Include: inc:
pass