Skip to content

Commit 1426bc5

Browse files
kitchoicorranwebsteraaronayres35Poruri Sai Rahul
authored
Backport documentation fixes and bugfixes for 7.1.0 release (#777)
* Add a section to the documentation on the basics of Pyface Widgets. (#739) (cherry picked from commit 86c9a9c) * avoid importing ArrayDataModel if numpy is not installed (#749) * avoid importing ArrayDataModel if numpy is not installed * replace try except with look-before-you-leap approach * typo (cherry picked from commit a68eb28) * Add api.py to data view packages (#750) * Add/update api.py modules for data views. * Use data view api modules in examples. * Add data view api modules to documentation examples. * Add some extra imports, change import locations. * Test API modules in pyface.data_view (#752) * Add test for pyface.data_view.api * Add test for pyface.data_view.exporters.api * Add test for data models API Make sure the api module is importable even if we don't have NumPy * Add tests to help developers keeping the list up-to-date * Fix language in a comment * Remove mixins from .api. * Adjust tests. Co-authored-by: Kit Choi <kitchoi@users.noreply.github.com> (cherry picked from commit e9b7d96) * Mention the data view API being provisional in the User Manual (#758) (cherry picked from commit cfb3f8c) * Set comparison mode to identity for MDataViewWidget.exporters (#759) (cherry picked from commit d5f5e7f) * Skip tests packages in API documentation (#761) (cherry picked from commit 9f13097) * Skip load_tests in API documentation (#762) * Skip load_tests in autodoc * Local flake8 (cherry picked from commit a3ad0f2) * Additional documentation for the DataView (#763) * Add documentation on Drag and Drop. * Add a note about DataViewGetError. * More notes on value types. * Apply suggestions from code review Co-authored-by: Kit Choi <kitchoi@users.noreply.github.com> * Fix references to exporters. Co-authored-by: Kit Choi <kitchoi@users.noreply.github.com> (cherry picked from commit 3acd644) * FIX docs click command to work on windows (#764) * FIX : Docs build on windows modified: etstool.py * Update etstool.py Co-authored-by: Kit Choi <kitchoi@users.noreply.github.com> Co-authored-by: Kit Choi <kitchoi@users.noreply.github.com> (cherry picked from commit bac64de) * CLN : Rename api-docs click command to docs (#766) Now, traitsui and pyface have the same command name - reducing unnecessary cognitive overhead. modified: etstool.py (cherry picked from commit 3a6d349) * FIX : Correct a docstring (#767) (cherry picked from commit 95d0474) * Get ModalDialogTester tests working on pyqt5 (#768) * FIX : Get ModalDialogTester tests working on pyqt5 The tests were previously being skipped because they failed mysteriously on pyqt5 - on further investigation, I saw weird errors related to two of the tests - a missing AttributeError for self.gui modified: pyface/ui/qt4/util/tests/test_modal_dialog_tester.py * FIX : Reverse order of superclasses modified: pyface/ui/qt4/util/tests/test_modal_dialog_tester.py (cherry picked from commit 96b8580) * Address sphinx warnings when building docs (#769) * FIX : Address sphinx warnings when building docs * FIX : Revert a confusing change (i couldnt come up with a worse commit message) modified: pyface/timer/do_later.py (cherry picked from commit 5b21b49) * Explicitly extract data from bytearrays rather than rely on wrapper. (#773) (cherry picked from commit 0d5565f) * Update changelog Co-authored-by: Corran Webster <cwebster@enthought.com> Co-authored-by: aaronayres35 <36972686+aaronayres35@users.noreply.github.com> Co-authored-by: Poruri Sai Rahul <rporuri@enthought.com>
1 parent 5818182 commit 1426bc5

38 files changed

+588
-61
lines changed

CHANGES.txt

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,10 @@ Build and continuous integration
6767

6868
Documentation
6969

70+
* Add documentation for the new PyfaceColor trait and Color class. (#710)
71+
* Add documentation for DataView. (#543, #574, #763)
7072
* Remove all enaml examples. (#652)
73+
* Fix some Sphinx warnings while building documentation. (#769)
7174

7275
Maintenance and code organization
7376

docs/source/conf.py

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -225,3 +225,12 @@
225225
'IPython.frontend.wx',
226226
'IPython.frontend.wx.wx_frontend',
227227
]
228+
229+
230+
def autodoc_skip_member(app, what, name, obj, skip, options):
231+
# Skip load_tests
232+
return skip or name == "load_tests"
233+
234+
235+
def setup(app):
236+
app.connect('autodoc-skip-member', autodoc_skip_member)

docs/source/data_view.rst

Lines changed: 137 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,12 @@ Pyface DataViews
77
The Pyface DataView API allows visualization of hierarchical and
88
non-hierarchical tabular data.
99

10+
.. note::
11+
As of Pyface 7.1.0, the public API for DataView is provisional and may
12+
change in the future minor releases through until Pyface 8.0
13+
14+
.. See enthought/pyface#756 for removing the note.
15+
1016
Indexing
1117
--------
1218

@@ -90,6 +96,104 @@ Note: with the current implementations, the |selection| list should not be
9096
mutated, rather the entire list should be replaced on every change. This
9197
restriction may be relaxed in the future.
9298

99+
100+
Drag and Drop
101+
-------------
102+
103+
The |IDataViewWidget| interface provides hooks to support dragging the
104+
selected values out of the table, or dropping objects onto the data view.
105+
To provide cross-platform and cross-toolkit compatibility, drag and drop
106+
operations require the data that is being exported or imported to be
107+
converted to or from a bytestring in some MIME type.
108+
109+
The DataView infrastructure provides a |DataFormat| named tuple to
110+
encapsulate the process of converting different data objects to bytes.
111+
For string objects this conversion might be as simple as encoding the
112+
text as UTF-8 and declaring it to be a ``text/plain`` MIME type, but for
113+
more complex structures there is serialization and deserialization which
114+
needs to occur. The |DataFormat| objects are expected to provide the
115+
mimetype of the data, a function to serialize an object, and a function
116+
to deserialize bytes.
117+
118+
In practice the sorts of objects being dragged and dropped, can be
119+
classified as simple scalar values (such as might occur when the selection
120+
is a single item), 1D collections of values (such as might occur when
121+
multiple items are selected, or a single row or column is selected),
122+
or 2D collections of values (such as might occur for extended row or
123+
column selections).
124+
125+
The DataView api provides a standard data formats for plain text, CSV,
126+
and .npy format for scalar, 1D and 2D exports; HTML and JSON formats
127+
for scalar values, as well as standard serializers and deserializers
128+
for users to create build their own |DataFormat| instances if the defaults
129+
do not match the needs.
130+
131+
Dragging
132+
~~~~~~~~
133+
134+
To allow dragging the selection, the |exporters| trait should hold a list
135+
of |AbstractDataExporter| instances. This class provides methods to access
136+
the values to be exported from the selected indices, as well as a reference
137+
to a |DataFormat| that will perform the actual serialization and provides
138+
the MIME type.
139+
140+
In practice, users will usually use a standard data exporter, such as the
141+
|ItemExporter| or |RowExporter|. Some care should be taken that
142+
the data exporter provides data in the shape that the |DataFormat| expects.
143+
For example, the |ItemExporter| works best when paired with scalar data
144+
formats. In many cases all that is needed to enable dragging data from a
145+
DataViewWidget is to configure it appropriately:
146+
147+
.. code-block:: python
148+
149+
control = DataViewWidget(
150+
...,
151+
selection_mode='extended',
152+
exporters=[
153+
RowExporter(format=table_format),
154+
RowExporter(format=csv_format),
155+
],
156+
...
157+
)
158+
159+
When multiple exporters are provided, _all_ of the supported formats are
160+
exported as part of the drag operation, and it is up to the target program
161+
to decide which of the supplied formats it can best handle, if any.
162+
163+
Dropping
164+
~~~~~~~~
165+
166+
The |IDataViewWidget| supports dropping of objects via the |IDropHandler|
167+
interface supported by other widgets. Developers using DataViews can
168+
handle dropped data by providing a list of |IDropHandler| instances which
169+
tell the underlying code whether the objects being dropped can be dropped,
170+
and if so, how to handle the drop operation.
171+
172+
For example, to handle files being dropped onto the DataView, a DataView could
173+
use the generic |FileDropHandler| class, coupled with a callback to load the
174+
data from the dropped file.
175+
176+
.. code-block:: python
177+
178+
control = DataViewWidget(
179+
...,
180+
drop_handlers=[
181+
FileDropHandler(
182+
extensions=['.csv', '.tsv', '.npy'],
183+
open_file=self.load_data,
184+
)
185+
],
186+
...
187+
)
188+
189+
When multiple drop handlers are supplied, the first one which says it can
190+
handle the dropped objects is the one which is used.
191+
192+
There are currently no specific drop handlers for supporting dragging
193+
data within the table, but this can be supported by custom drop handlers
194+
that use toolkit code to interact with the underlying toolkit objects.
195+
196+
93197
Index Managers
94198
--------------
95199

@@ -174,7 +278,8 @@ it corresponds to the keys or the values. The code looks like this:
174278
:end-at: return value
175279

176280
Conversion of values into data channels is done by providing a value type
177-
for each cell. The |get_value_type| method provides an appropriate data
281+
for each cell that implements the |AbstractValueType| interface. The
282+
|get_value_type| method is expected to provide an appropriate data
178283
type for each item in the table. For this data model we have three value
179284
types: the column headers, the keys and the values.
180285

@@ -196,6 +301,27 @@ value types:
196301
:start-at: def get_value_type
197302
:end-at: return self.value_type
198303

304+
The |AbstractValueType| interface provides getters (and in some cases setters)
305+
for various data channels the most obvious of these is the text to display
306+
in an item, but channels allow checked state, image, color and tooltips
307+
to also be associated with a value. How (or even if) these values are
308+
displayed or used is up to the implementation of the |IDataViewWidget|.
309+
310+
As noted above, the DataView API provides a number of pre-definited value
311+
type implementations that cover common cases, but where they do not meet the
312+
needs of a particular design, developers should create their own
313+
implementations with the desired properties.
314+
315+
Invalid Values
316+
~~~~~~~~~~~~~~
317+
318+
If no valid value can be generated for some *expected* reason, value
319+
generation code can raise a |DataViewGetError| exception. This error
320+
will be handled and silently ignored by the DataView code, and no value
321+
will be displayed. Any other errors raised by value generation are
322+
assumed to be unexpected and will be logged and re-raised, which is
323+
likely to cause an application crash.
324+
199325
Handling Updates
200326
~~~~~~~~~~~~~~~~
201327

@@ -275,11 +401,19 @@ the |has_editor_value| method returns ``False``.
275401
276402
.. |AbstractIndexManager| replace:: :py:class:`~pyface.data_view.index_manager.AbstractIndexManager`
277403
.. |AbstractDataModel| replace:: :py:class:`~pyface.data_view.abstract_data_model.AbstractDataModel`
278-
.. |DataViewSetError| replace:: :py:class:`~pyface.data_view.abstract_data_model.DataViewSetError`
404+
.. |AbstractDataExporter| replace:: :py:class:`~pyface.data_view.abstract_data_exporter.AbstractDataExporter`
405+
.. |AbstractValueType| replace:: :py:class:`~pyface.data_view.abstract_value_type.AbstractValueType`
406+
.. |DataFormat| replace:: :py:class:`~pyface.data_view.i_data_wrapper.DataFormat`
407+
.. |DataViewGetError| replace:: :py:class:`~pyface.data_view.data_view_errors.DataViewGetError`
408+
.. |DataViewSetError| replace:: :py:class:`~pyface.data_view.data_view_errors.DataViewSetError`
279409
.. |EditableValue| replace:: :py:class:`~pyface.data_view.value_types.editable_value.EditableValue`
410+
.. |FileDropHandler| replace:: :py:class:`~pyface.drop_handler.FileDropHandler`
280411
.. |IDataViewWidget| replace:: :py:class:`~pyface.data_view.i_data_view_widget.IDataViewWidget`
412+
.. |IDropHandler| replace:: :py:class:`~pyface.i_drop_handler.IDropHandler`
281413
.. |IntIndexManager| replace:: :py:class:`~pyface.data_view.index_manager.IntIndexManager`
282414
.. |IntValue| replace:: :py:class:`~pyface.data_view.value_types.numeric_value.IntValue`
415+
.. |ItemExporter| replace:: :py:class:`~pyface.data_view.exporters.item_exporter.ItemExporter`
416+
.. |RowExporter| replace:: :py:class:`~pyface.data_view.exporters.row_exporter.RowExporter`
283417
.. |TextValue| replace:: :py:class:`~pyface.data_view.value_types.text_value.TextValue`
284418
.. |TupleIndexManager| replace:: :py:class:`~pyface.data_view.index_manager.TupleIndexManager`
285419
.. |can_have_children| replace:: :py:meth:`~pyface.data_view.abstract_data_model.AbstractDataModel.can_have_children`
@@ -289,6 +423,7 @@ the |has_editor_value| method returns ``False``.
289423
.. |get_value| replace:: :py:meth:`~pyface.data_view.abstract_data_model.AbstractDataModel.get_value`
290424
.. |get_value_type| replace:: :py:meth:`~pyface.data_view.abstract_data_model.AbstractDataModel.get_value`
291425
.. |has_editor_value| replace:: :py:meth:`~pyface.data_view.abstract_value_type.AbstractValueType.has_editor_value`
426+
.. |exporters| replace:: :py:attr:`~pyface.data_view.i_data_view_widget.IDataViewWidget.exporters`
292427
.. |selection| replace:: :py:attr:`~pyface.data_view.i_data_view_widget.IDataViewWidget.selection`
293428
.. |selection_mode| replace:: :py:attr:`~pyface.data_view.i_data_view_widget.IDataViewWidget.selection_mode`
294429
.. |selection_type| replace:: :py:attr:`~pyface.data_view.i_data_view_widget.IDataViewWidget.selection_type`

docs/source/examples/data_model_indices.py

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,8 +10,7 @@
1010

1111
from traits.api import Instance, Int, List
1212

13-
from pyface.data_view.abstract_data_model import AbstractDataModel
14-
from pyface.data_view.index_manager import TupleIndexManager
13+
from pyface.data_view.api import AbstractDataModel, TupleIndexManager
1514

1615

1716
class IndexDataModel(AbstractDataModel):

docs/source/examples/dict_data_model.py

Lines changed: 2 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -10,11 +10,9 @@
1010

1111
from traits.api import ComparisonMode, Dict, Instance, Str, observe
1212

13-
from pyface.data_view.abstract_data_model import (
14-
AbstractDataModel, DataViewSetError
13+
from pyface.data_view.api import (
14+
AbstractDataModel, AbstractValueType, DataViewSetError, IntIndexManager
1515
)
16-
from pyface.data_view.abstract_value_type import AbstractValueType
17-
from pyface.data_view.index_manager import IntIndexManager
1816

1917

2018
class DictDataModel(AbstractDataModel):
@@ -121,7 +119,6 @@ def _value_type_default(self):
121119
from pyface.data_view.data_view_widget import DataViewWidget
122120
from pyface.data_view.value_types.api import IntValue, TextValue
123121

124-
125122
class MainWindow(ApplicationWindow):
126123
""" The main application window. """
127124

@@ -144,7 +141,6 @@ def destroy(self):
144141
self.data_view.destroy()
145142
super().destroy()
146143

147-
148144
# Create the GUI (this does NOT start the GUI event loop).
149145
gui = GUI()
150146

docs/source/fields.rst

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
.. _fields:
2+
13
======
24
Fields
35
======

docs/source/index.rst

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -73,8 +73,9 @@ Contents
7373

7474
Overview <overview>
7575
Toolkits <toolkits>
76-
Submodules <submodules>
76+
Widgets <widgets>
7777
Pyface Applications <applications>
7878
Pyface Trait Types <traits>
79+
Submodules <submodules>
7980
API Documentation <api/pyface>
8081
Change Log <changelog>

docs/source/overview.rst

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
.. _overview:
2+
13
========
24
Overview
35
========

0 commit comments

Comments
 (0)