diff options
Diffstat (limited to 'grc/src')
-rw-r--r-- | grc/src/Makefile.am | 12 | ||||
-rw-r--r-- | grc/src/__init__.py | 1 | ||||
-rw-r--r-- | grc/src/grc/Constants.py.in | 154 | ||||
-rw-r--r-- | grc/src/grc/elements/__init__.py | 21 | ||||
-rw-r--r-- | grc/src/grc/gui/__init__.py | 26 | ||||
-rw-r--r-- | grc/src/grc/gui/elements/__init__.py | 22 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/Makefile.am | 34 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/__init__.py | 19 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/blks2/Makefile.am | 4 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/blks2/__init__.py | 11 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/blks2/error_rate.py | 45 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/blks2/packet.py | 72 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/blks2/queue.py | 71 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/blks2/selector.py | 85 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/usrp/Makefile.am | 4 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/usrp/__init__.py | 11 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/usrp/simple_usrp.py | 55 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/utils/__init__.py | 21 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/wxgui/Makefile.am | 4 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/wxgui/__init__.py | 11 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/wxgui/callback_controls.py | 32 | ||||
-rw-r--r-- | grc/src/grc_gnuradio/wxgui/top_block_gui.py | 11 | ||||
-rw-r--r-- | grc/src/gui/ActionHandler.py (renamed from grc/src/grc/ActionHandler.py) | 256 | ||||
-rw-r--r-- | grc/src/gui/Actions.py (renamed from grc/src/grc/Actions.py) | 6 | ||||
-rw-r--r-- | grc/src/gui/Bars.py (renamed from grc/src/grc/gui/Bars.py) | 93 | ||||
-rw-r--r-- | grc/src/gui/BlockTreeWindow.py (renamed from grc/src/grc/gui/BlockTreeWindow.py) | 21 | ||||
-rw-r--r-- | grc/src/gui/Constants.py | 82 | ||||
-rw-r--r-- | grc/src/gui/Dialogs.py (renamed from grc/src/grc/gui/Dialogs.py) | 20 | ||||
-rw-r--r-- | grc/src/gui/DrawingArea.py (renamed from grc/src/grc/gui/DrawingArea.py) | 16 | ||||
-rw-r--r-- | grc/src/gui/FileDialogs.py (renamed from grc/src/grc/gui/FileDialogs.py) | 18 | ||||
-rw-r--r-- | grc/src/gui/MainWindow.py (renamed from grc/src/grc/gui/MainWindow.py) | 47 | ||||
-rw-r--r-- | grc/src/gui/Makefile.am (renamed from grc/src/grc/gui/Makefile.am) | 16 | ||||
-rw-r--r-- | grc/src/gui/Messages.py (renamed from grc/src/grc/Messages.py) | 25 | ||||
-rw-r--r-- | grc/src/gui/NotebookPage.py (renamed from grc/src/grc/gui/NotebookPage.py) | 35 | ||||
-rw-r--r-- | grc/src/gui/ParamsDialog.py (renamed from grc/src/grc/gui/ParamsDialog.py) | 15 | ||||
-rw-r--r-- | grc/src/gui/Preferences.py (renamed from grc/src/grc/Preferences.py) | 9 | ||||
-rw-r--r-- | grc/src/gui/StateCache.py (renamed from grc/src/grc/StateCache.py) | 35 | ||||
-rw-r--r-- | grc/src/gui/__init__.py | 1 | ||||
-rw-r--r-- | grc/src/platforms/Makefile.am | 31 | ||||
-rw-r--r-- | grc/src/platforms/__init__.py | 1 | ||||
-rw-r--r-- | grc/src/platforms/base/Block.py (renamed from grc/src/grc/elements/Block.py) | 28 | ||||
-rw-r--r-- | grc/src/platforms/base/Connection.py (renamed from grc/src/grc/elements/Connection.py) | 13 | ||||
-rw-r--r-- | grc/src/platforms/base/Constants.py.in (renamed from grc/src/grc/__init__.py) | 27 | ||||
-rw-r--r-- | grc/src/platforms/base/Element.py (renamed from grc/src/grc/elements/Element.py) | 3 | ||||
-rw-r--r-- | grc/src/platforms/base/FlowGraph.py (renamed from grc/src/grc/elements/FlowGraph.py) | 38 | ||||
-rw-r--r-- | grc/src/platforms/base/Makefile.am (renamed from grc/src/grc/Makefile.am) | 25 | ||||
-rw-r--r-- | grc/src/platforms/base/Param.py (renamed from grc/src/grc/elements/Param.py) | 21 | ||||
-rw-r--r-- | grc/src/platforms/base/Platform.py (renamed from grc/src/grc/elements/Platform.py) | 32 | ||||
-rw-r--r-- | grc/src/platforms/base/Port.py (renamed from grc/src/grc/elements/Port.py) | 16 | ||||
-rw-r--r-- | grc/src/platforms/base/__init__.py | 1 | ||||
-rw-r--r-- | grc/src/platforms/gui/Block.py (renamed from grc/src/grc/gui/elements/Block.py) | 26 | ||||
-rw-r--r-- | grc/src/platforms/gui/Colors.py (renamed from grc/src/grc/gui/elements/Colors.py) | 2 | ||||
-rw-r--r-- | grc/src/platforms/gui/Connection.py (renamed from grc/src/grc/gui/elements/Connection.py) | 10 | ||||
-rw-r--r-- | grc/src/platforms/gui/Constants.py | 44 | ||||
-rw-r--r-- | grc/src/platforms/gui/Element.py (renamed from grc/src/grc/gui/elements/Element.py) | 42 | ||||
-rw-r--r-- | grc/src/platforms/gui/FlowGraph.py (renamed from grc/src/grc/gui/elements/FlowGraph.py) | 78 | ||||
-rw-r--r-- | grc/src/platforms/gui/Makefile.am (renamed from grc/src/grc/gui/elements/Makefile.am) | 9 | ||||
-rw-r--r-- | grc/src/platforms/gui/Param.py (renamed from grc/src/grc/gui/elements/Param.py) | 16 | ||||
-rw-r--r-- | grc/src/platforms/gui/Platform.py (renamed from grc/src/grc/gui/elements/Platform.py) | 9 | ||||
-rw-r--r-- | grc/src/platforms/gui/Port.py (renamed from grc/src/grc/gui/elements/Port.py) | 31 | ||||
-rw-r--r-- | grc/src/platforms/gui/Utils.py (renamed from grc/src/grc/gui/elements/Utils.py) | 9 | ||||
-rw-r--r-- | grc/src/platforms/gui/__init__.py | 1 | ||||
-rw-r--r-- | grc/src/platforms/python/Block.py (renamed from grc/src/grc_gnuradio/Block.py) | 20 | ||||
-rw-r--r-- | grc/src/platforms/python/Connection.py (renamed from grc/src/grc_gnuradio/Connection.py) | 11 | ||||
-rw-r--r-- | grc/src/platforms/python/Constants.py.in (renamed from grc/src/grc_gnuradio/Constants.py.in) | 4 | ||||
-rw-r--r-- | grc/src/platforms/python/FlowGraph.py (renamed from grc/src/grc_gnuradio/FlowGraph.py) | 21 | ||||
-rw-r--r-- | grc/src/platforms/python/Generator.py (renamed from grc/src/grc_gnuradio/Generator.py) | 16 | ||||
-rw-r--r-- | grc/src/platforms/python/Makefile.am | 51 | ||||
-rw-r--r-- | grc/src/platforms/python/Param.py (renamed from grc/src/grc_gnuradio/Param.py) | 13 | ||||
-rw-r--r-- | grc/src/platforms/python/Platform.py (renamed from grc/src/grc_gnuradio/Platform.py) | 16 | ||||
-rw-r--r-- | grc/src/platforms/python/Port.py (renamed from grc/src/grc_gnuradio/Port.py) | 17 | ||||
-rw-r--r-- | grc/src/platforms/python/__init__.py | 1 | ||||
-rw-r--r-- | grc/src/platforms/python/utils/Makefile.am (renamed from grc/src/grc_gnuradio/utils/Makefile.am) | 8 | ||||
-rw-r--r-- | grc/src/platforms/python/utils/__init__.py | 1 | ||||
-rw-r--r-- | grc/src/platforms/python/utils/convert_hier.py (renamed from grc/src/grc_gnuradio/utils/convert_hier.py) | 8 | ||||
-rw-r--r-- | grc/src/platforms/python/utils/expr_utils.py (renamed from grc/src/grc_gnuradio/utils/expr_utils.py) | 14 | ||||
-rw-r--r-- | grc/src/platforms/python/utils/extract_docs.py (renamed from grc/src/grc_gnuradio/utils/extract_docs.py) | 10 | ||||
-rw-r--r-- | grc/src/utils/Makefile.am (renamed from grc/src/grc/elements/Makefile.am) | 15 | ||||
-rw-r--r-- | grc/src/utils/ParseXML.py (renamed from grc/src/grc/ParseXML.py) | 14 | ||||
-rw-r--r-- | grc/src/utils/__init__.py (renamed from grc/src/grc/Utils.py) | 3 | ||||
-rw-r--r-- | grc/src/utils/converter.py (renamed from grc/src/grc/converter.py) | 21 |
81 files changed, 1025 insertions, 1173 deletions
diff --git a/grc/src/Makefile.am b/grc/src/Makefile.am index 01c35d58b..a726d4935 100644 --- a/grc/src/Makefile.am +++ b/grc/src/Makefile.am @@ -19,6 +19,14 @@ # Boston, MA 02110-1301, USA. # -include $(top_srcdir)/Makefile.common +include $(top_srcdir)/grc/Makefile.inc -SUBDIRS = grc grc_gnuradio +SUBDIRS = \ + platforms \ + grc_gnuradio \ + gui \ + utils + +ourpythondir = $(grc_src_prefix) + +ourpython_PYTHON = __init__.py diff --git a/grc/src/__init__.py b/grc/src/__init__.py new file mode 100644 index 000000000..8b1378917 --- /dev/null +++ b/grc/src/__init__.py @@ -0,0 +1 @@ + diff --git a/grc/src/grc/Constants.py.in b/grc/src/grc/Constants.py.in deleted file mode 100644 index a16715080..000000000 --- a/grc/src/grc/Constants.py.in +++ /dev/null @@ -1,154 +0,0 @@ -""" -Copyright 2008 Free Software Foundation, Inc. -This file is part of GNU Radio - -GNU Radio Companion is free software; you can redistribute it and/or -modify it under the terms of the GNU General Public License -as published by the Free Software Foundation; either version 2 -of the License, or (at your option) any later version. - -GNU Radio Companion is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA -""" -##@package grc.Constants -#Global constants -#@author Josh Blum - -import os - -###################################################################################################### -## Global Titles -###################################################################################################### - -##The current version of this code -VERSION = '@VERSION@' - -##The name to appear in the main window for a flow graph that has not been saved to file. -NEW_FLOGRAPH_TITLE = 'untitled' - -##The prefix title on the main window. -MAIN_WINDOW_PREFIX = "GRC" - -###################################################################################################### -## Signal block connector lengths -###################################################################################################### - -##The length that a connection must extend from the port until the length depends on the index of the port. -CONNECTOR_EXTENSION_INITIAL_LENGTH = 11 - -##The length that a connection must extend from the initial length times the index of the port, after this length, the connection may have a bend. -CONNECTOR_EXTENSION_LENGTH = 11 - -##The length of the connector arrow base in pixels -CONNECTOR_ARROW_BASE = 13 - -##The length of the connector arrow height in pixels -CONNECTOR_ARROW_HEIGHT = 17 - -###################################################################################################### -## Signal block rotations -###################################################################################################### - -##List of possible angles (in degrees) that a block can be rotated to. -POSSIBLE_ROTATIONS = (0, 90, 180, 270) - -##direction of rotation left. -DIR_LEFT = 'left' - -##direction of rotation right. -DIR_RIGHT = 'right' - -###################################################################################################### -## Dimension constraints for the various windows (in pixels) -###################################################################################################### - -##main window constraints -MIN_WINDOW_WIDTH = 600 -MIN_WINDOW_HEIGHT = 400 - -##dialog constraints -MIN_DIALOG_WIDTH = 500 -MIN_DIALOG_HEIGHT = 500 - -##static height of reports window -REPORTS_WINDOW_HEIGHT = 100 - -##static width of block selection window -BLOCK_SELECTION_WINDOW_WIDTH = 200 - -###################################################################################################### -## Constraints on displayable labels and ports -###################################################################################################### - -LABEL_SEPARATION = 3 -LABEL_PADDING_WIDTH = 9 -LABEL_PADDING_HEIGHT = 9 - -PORT_SEPARATION = 17 -PORT_HEIGHT = 15 -PORT_WIDTH = 25 -PORT_BORDER_SEPARATION = 9 -MAX_NUM_PORTS = 7 - -PARAM_LABEL_FONT = 'Sans 9.5' -PARAM_FONT = 'Sans 7.5' -BLOCK_FONT = 'Sans 8' -PORT_FONT = 'Sans 7.5' - -###################################################################################################### -## Dragging, scrolling, and redrawing constants for the flow graph window in pixels -###################################################################################################### - -##How close can the mouse get to the window border before mouse events are ignored. -BORDER_PROXIMITY_SENSITIVITY = 50 - -##How close the mouse can get to the edge of the visible window before scrolling is invoked. -SCROLL_PROXIMITY_SENSITIVITY = 30 - -##When the window has to be scrolled, move it this distance in the required direction. -SCROLL_DISTANCE = 15 - -##The redrawing sensitivity, how many seconds must pass between motion events before a redraw? -MOTION_DETECT_REDRAWING_SENSITIVITY = .02 - -##How close the mouse click can be to a connection and register a connection select. -CONNECTION_SELECT_SENSITIVITY = 5 - -###################################################################################################### -# A state is recorded for each change to the flow graph, the size dictates how many states we can record -###################################################################################################### - -##The size of the state saving cache in the flow graph (for undo/redo functionality) -STATE_CACHE_SIZE = 42 - -###################################################################################################### -## Constansts dealing with File Paths -###################################################################################################### - -##Location of external data files. -DATA_DIR = '@datadir@' - -##DTD validator for saved flow graphs. -FLOW_GRAPH_DTD = os.path.join(DATA_DIR, 'flow_graph.dtd') - -##The default file extension for flow graphs. -FLOW_GRAPH_FILE_EXTENSION = '.grc' - -##The default file extension for saving flow graph snap shots. -IMAGE_FILE_EXTENSION = '.png' - -##The default path for the open/save dialogs. -DEFAULT_FILE_PATH = os.getcwd() - -##The default icon for the gtk windows. -PY_GTK_ICON = os.path.join(DATA_DIR, 'grc-icon-256.png') - -##The users home directory. -HOME_DIR = os.path.expanduser('~') - diff --git a/grc/src/grc/elements/__init__.py b/grc/src/grc/elements/__init__.py deleted file mode 100644 index cb5e282ec..000000000 --- a/grc/src/grc/elements/__init__.py +++ /dev/null @@ -1,21 +0,0 @@ -""" -Copyright 2008 Free Software Foundation, Inc. -This file is part of GNU Radio - -GNU Radio Companion is free software; you can redistribute it and/or -modify it under the terms of the GNU General Public License -as published by the Free Software Foundation; either version 2 -of the License, or (at your option) any later version. - -GNU Radio Companion is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA -""" -##@package grc.elements -#Package for flow graph elements. - diff --git a/grc/src/grc/gui/__init__.py b/grc/src/grc/gui/__init__.py deleted file mode 100644 index 0e92cb11e..000000000 --- a/grc/src/grc/gui/__init__.py +++ /dev/null @@ -1,26 +0,0 @@ -""" -Copyright 2007 Free Software Foundation, Inc. -This file is part of GNU Radio - -GNU Radio Companion is free software; you can redistribute it and/or -modify it under the terms of the GNU General Public License -as published by the Free Software Foundation; either version 2 -of the License, or (at your option) any later version. - -GNU Radio Companion is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA -""" -##@package grc.gui -#GTK based classes go into this package. - -#only import the modules that need external access -from MainWindow import MainWindow -from FileDialogs import OpenFlowGraphFileDialog,SaveFlowGraphFileDialog,SaveImageFileDialog -from Dialogs import PreferencesDialog,MessageDialogHelper,AboutDialog,HotKeysDialog - diff --git a/grc/src/grc/gui/elements/__init__.py b/grc/src/grc/gui/elements/__init__.py deleted file mode 100644 index e79167aab..000000000 --- a/grc/src/grc/gui/elements/__init__.py +++ /dev/null @@ -1,22 +0,0 @@ -""" -Copyright 2007 Free Software Foundation, Inc. -This file is part of GNU Radio - -GNU Radio Companion is free software; you can redistribute it and/or -modify it under the terms of the GNU General Public License -as published by the Free Software Foundation; either version 2 -of the License, or (at your option) any later version. - -GNU Radio Companion is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA -""" -##@package grc.gui.elements -#All graphical elements used in a flow graph. - - diff --git a/grc/src/grc_gnuradio/Makefile.am b/grc/src/grc_gnuradio/Makefile.am index bcee51899..767e8f670 100644 --- a/grc/src/grc_gnuradio/Makefile.am +++ b/grc/src/grc_gnuradio/Makefile.am @@ -21,33 +21,11 @@ include $(top_srcdir)/grc/Makefile.inc -SUBDIRS = blks2 usrp utils wxgui +SUBDIRS = \ + blks2 \ + usrp \ + wxgui -ourpythondir = $(pythondir)/grc_gnuradio +ourpythondir = $(grc_gnuradio_prefix) -ourpython_PYTHON = \ - __init__.py \ - Constants.py \ - Block.py \ - Connection.py \ - FlowGraph.py \ - Generator.py \ - Platform.py \ - Param.py \ - Port.py - -docdir = $(prefix)/share/doc/@PACKAGE@-@VERSION@ - -BUILT_SOURCES = Constants.py - -Constants.py: Makefile $(srcdir)/Constants.py.in - sed \ - -e 's|@PYTHONW[@]|$(PYTHONW)|g' \ - -e 's|@datadir[@]|$(grc_gnuradio_data_dir)|g' \ - -e 's|@blocksdir[@]|$(grc_gnuradio_blocks_dir)|g' \ - -e 's|@docdir[@]|$(docdir)|g' \ - $(srcdir)/Constants.py.in > $@ - -EXTRA_DIST = Constants.py.in - -MOSTLYCLEANFILES = $(BUILT_SOURCES) +ourpython_PYTHON = __init__.py diff --git a/grc/src/grc_gnuradio/__init__.py b/grc/src/grc_gnuradio/__init__.py index eac305165..8b1378917 100644 --- a/grc/src/grc_gnuradio/__init__.py +++ b/grc/src/grc_gnuradio/__init__.py @@ -1,20 +1 @@ -""" -Copyright 2008 Free Software Foundation, Inc. -This file is part of GNU Radio -GNU Radio Companion is free software; you can redistribute it and/or -modify it under the terms of the GNU General Public License -as published by the Free Software Foundation; either version 2 -of the License, or (at your option) any later version. - -GNU Radio Companion is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA -""" -##@package grc_gnuradio -#gnuradio overloaded elements and supplemental python modules diff --git a/grc/src/grc_gnuradio/blks2/Makefile.am b/grc/src/grc_gnuradio/blks2/Makefile.am index 307ec863f..e3a0b8a38 100644 --- a/grc/src/grc_gnuradio/blks2/Makefile.am +++ b/grc/src/grc_gnuradio/blks2/Makefile.am @@ -19,9 +19,9 @@ # Boston, MA 02110-1301, USA. # -include $(top_srcdir)/Makefile.common +include $(top_srcdir)/grc/Makefile.inc -ourpythondir = $(pythondir)/grc_gnuradio/blks2 +ourpythondir = $(grc_gnuradio_prefix)/blks2 ourpython_PYTHON = \ __init__.py \ diff --git a/grc/src/grc_gnuradio/blks2/__init__.py b/grc/src/grc_gnuradio/blks2/__init__.py index cd1b793c4..a26228f88 100644 --- a/grc/src/grc_gnuradio/blks2/__init__.py +++ b/grc/src/grc_gnuradio/blks2/__init__.py @@ -1,22 +1,22 @@ # Copyright 2008 Free Software Foundation, Inc. -# +# # This file is part of GNU Radio -# +# # GNU Radio is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3, or (at your option) # any later version. -# +# # GNU Radio is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. -# +# # You should have received a copy of the GNU General Public License # along with GNU Radio; see the file COPYING. If not, write to # the Free Software Foundation, Inc., 51 Franklin Street, # Boston, MA 02110-1301, USA. -# +# from queue import queue_sink_thread from queue import queue_sink_c, queue_sink_f, queue_sink_i, queue_sink_s, queue_sink_b @@ -25,4 +25,3 @@ from queue import queue_source_c, queue_source_f, queue_source_i, queue_source_s from selector import selector, valve from packet import packet_encoder, packet_decoder from error_rate import error_rate - diff --git a/grc/src/grc_gnuradio/blks2/error_rate.py b/grc/src/grc_gnuradio/blks2/error_rate.py index eb09940cb..9b2df58ef 100644 --- a/grc/src/grc_gnuradio/blks2/error_rate.py +++ b/grc/src/grc_gnuradio/blks2/error_rate.py @@ -1,22 +1,22 @@ # Copyright 2008 Free Software Foundation, Inc. -# +# # This file is part of GNU Radio -# +# # GNU Radio is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3, or (at your option) # any later version. -# +# # GNU Radio is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. -# +# # You should have received a copy of the GNU General Public License # along with GNU Radio; see the file COPYING. If not, write to # the Free Software Foundation, Inc., 51 Franklin Street, # Boston, MA 02110-1301, USA. -# +# default_win_size = 1000 @@ -31,7 +31,7 @@ class input_watcher(_threading.Thread): """ Read samples from the message queue and hand them to the callback. """ - + def __init__(self, msgq, callback): self._msgq = msgq self._callback = callback @@ -39,7 +39,7 @@ class input_watcher(_threading.Thread): self.setDaemon(1) self.keep_running = True self.start() - + def run(self): r = '' while True: @@ -49,27 +49,27 @@ class input_watcher(_threading.Thread): s = r + msg.to_string() i = (nitems-nitems%2)*itemsize r = s[i:] - s = s[:i] + s = s[:i] samples = numpy.fromstring(s, numpy.int8) - self._callback(samples) - + self._callback(samples) + class error_rate(gr.hier_block2): """ Sample the incoming data streams (byte) and calculate the bit or symbol error rate. Write the running rate to the output data stream (float). """ - - def __init__(self, type='BER', win_size=default_win_size, bits_per_symbol=2): - """! + + def __init__(self, type='BER', win_size=default_win_size, bits_per_symbol=2): + """ Error rate constructor. @param type a string 'BER' or 'SER' @param win_size the number of samples to calculate over @param bits_per_symbol the number of information bits per symbol (BER only) - """ + """ #init gr.hier_block2.__init__( - self, 'error_rate', - gr.io_signature(2, 2, gr.sizeof_char), + self, 'error_rate', + gr.io_signature(2, 2, gr.sizeof_char), gr.io_signature(1, 1, gr.sizeof_float), ) assert type in ('BER', 'SER') @@ -95,12 +95,12 @@ class error_rate(gr.hier_block2): self.connect((self, 0), (inter, 0)) self.connect((self, 1), (inter, 1)) self.connect(inter, msg_sink) - + def _handler_ber(self, samples): num = len(samples)/2 arr = numpy.zeros(num, numpy.float32) for i in range(num): - old_err = self._err_array[self._err_index] + old_err = self._err_array[self._err_index] #record error self._err_array[self._err_index] = _1s_counts[samples[i*2] ^ samples[i*2 + 1]] self._num_errs = self._num_errs + self._err_array[self._err_index] - old_err @@ -111,13 +111,13 @@ class error_rate(gr.hier_block2): arr[i] = float(self._num_errs)/float(self._num_samps*self._bits_per_symbol) #write message msg = gr.message_from_string(arr.tostring(), 0, gr.sizeof_float, num) - self._msgq_source.insert_tail(msg) - + self._msgq_source.insert_tail(msg) + def _handler_ser(self, samples): num = len(samples)/2 arr = numpy.zeros(num, numpy.float32) for i in range(num): - old_err = self._err_array[self._err_index] + old_err = self._err_array[self._err_index] #record error ref = samples[i*2] res = samples[i*2 + 1] @@ -134,5 +134,4 @@ class error_rate(gr.hier_block2): arr[i] = float(self._num_errs)/float(self._num_samps) #write message msg = gr.message_from_string(arr.tostring(), 0, gr.sizeof_float, num) - self._msgq_source.insert_tail(msg) - + self._msgq_source.insert_tail(msg) diff --git a/grc/src/grc_gnuradio/blks2/packet.py b/grc/src/grc_gnuradio/blks2/packet.py index 5276de109..fcdfb9ae2 100644 --- a/grc/src/grc_gnuradio/blks2/packet.py +++ b/grc/src/grc_gnuradio/blks2/packet.py @@ -1,22 +1,22 @@ # Copyright 2008 Free Software Foundation, Inc. -# +# # This file is part of GNU Radio -# +# # GNU Radio is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3, or (at your option) # any later version. -# +# # GNU Radio is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. -# +# # You should have received a copy of the GNU General Public License # along with GNU Radio; see the file COPYING. If not, write to # the Free Software Foundation, Inc., 51 Franklin Street, # Boston, MA 02110-1301, USA. -# +# from gnuradio import gr, packet_utils import gnuradio.gr.gr_threading as _threading @@ -31,11 +31,11 @@ DEFAULT_MSGQ_LIMIT = 2 DEFAULT_THRESHOLD = 12 ####################################################################################### -## Packet Encoder +## Packet Encoder ####################################################################################### class _packet_encoder_thread(_threading.Thread): - + def __init__(self, msgq, payload_length, send): self._msgq = msgq self._payload_length = payload_length @@ -44,24 +44,24 @@ class _packet_encoder_thread(_threading.Thread): self.setDaemon(1) self.keep_running = True self.start() - + def run(self): sample = '' #residual sample while self.keep_running: msg = self._msgq.delete_head() #blocking read of message queue - sample = sample + msg.to_string() #get the body of the msg as a string - while len(sample) >= self._payload_length: + sample = sample + msg.to_string() #get the body of the msg as a string + while len(sample) >= self._payload_length: payload = sample[0:self._payload_length] - sample = sample[self._payload_length:] - self._send(payload) + sample = sample[self._payload_length:] + self._send(payload) class packet_encoder(gr.hier_block2): """ Hierarchical block for wrapping packet-based modulators. """ - + def __init__(self, item_size_in, samples_per_symbol, bits_per_symbol, access_code='', pad_for_usrp=True, payload_length=-1): - """! + """ packet_mod constructor. @param item_size_in the size of the input data stream in bytes @param samples_per_symbol number of samples per symbol @@ -79,8 +79,8 @@ class packet_encoder(gr.hier_block2): access_code = packet_utils.default_access_code if not packet_utils.is_1_0_string(access_code): raise ValueError, "Invalid access_code %r. Must be string of 1's and 0's" % (access_code,) - self._access_code = access_code - self._pad_for_usrp = pad_for_usrp + self._access_code = access_code + self._pad_for_usrp = pad_for_usrp if payload_length < 0: #get payload length payload_length = DEFAULT_PAYLOAD_LEN if payload_length%self._item_size_in != 0: #verify that packet length is a multiple of the stream size @@ -88,12 +88,12 @@ class packet_encoder(gr.hier_block2): self._payload_length = payload_length #create blocks msg_source = gr.message_source(gr.sizeof_char, DEFAULT_MSGQ_LIMIT) - self._msgq_out = msg_source.msgq() + self._msgq_out = msg_source.msgq() self._msgq_in = gr.msg_queue(DEFAULT_MSGQ_LIMIT) - msg_sink = gr.message_sink(self._item_size_in, self._msgq_in, False) #False -> blocking + msg_sink = gr.message_sink(self._item_size_in, self._msgq_in, False) #False -> blocking #initialize hier2 gr.hier_block2.__init__( - self, + self, "packet_encoder", gr.io_signature(1, 1, self._item_size_in), # Input signature gr.io_signature(1, 1, gr.sizeof_char) # Output signature @@ -103,12 +103,12 @@ class packet_encoder(gr.hier_block2): self.connect(msg_source, self) #start thread _packet_encoder_thread(self._msgq_in, self._payload_length, self._send_packet) - + def _send_packet(self, payload): - """! + """ Wrap the payload in a packet and push onto the message queue. @param payload string, data to send - """ + """ packet = packet_utils.make_packet( payload, self._samples_per_symbol, @@ -118,13 +118,13 @@ class packet_encoder(gr.hier_block2): ) msg = gr.message_from_string(packet) self._msgq_out.insert_tail(msg) - + ####################################################################################### -## Packet Decoder +## Packet Decoder ####################################################################################### class _packet_decoder_thread(_threading.Thread): - + def __init__(self, msgq, callback): _threading.Thread.__init__(self) self.setDaemon(1) @@ -144,9 +144,9 @@ class packet_decoder(gr.hier_block2): """ Hierarchical block for wrapping packet-based demodulators. """ - + def __init__(self, item_size_out, access_code='', threshold=-1): - """! + """ packet_demod constructor. @param item_size_out the size of the output data stream in bytes @param access_code AKA sync vector @@ -159,19 +159,19 @@ class packet_decoder(gr.hier_block2): access_code = packet_utils.default_access_code if not packet_utils.is_1_0_string(access_code): raise ValueError, "Invalid access_code %r. Must be string of 1's and 0's" % (access_code,) - self._access_code = access_code + self._access_code = access_code #threshold - if threshold < 0: threshold = DEFAULT_THRESHOLD - self._threshold = threshold + if threshold < 0: threshold = DEFAULT_THRESHOLD + self._threshold = threshold #blocks self._msgq_in = gr.msg_queue(DEFAULT_MSGQ_LIMIT) #holds packets from the PHY correlator = gr.correlate_access_code_bb(self._access_code, self._threshold) - framer_sink = gr.framer_sink_1(self._msgq_in) + framer_sink = gr.framer_sink_1(self._msgq_in) msg_source = gr.message_source(self._item_size_out, DEFAULT_MSGQ_LIMIT) - self._msgq_out = msg_source.msgq() + self._msgq_out = msg_source.msgq() #initialize hier2 gr.hier_block2.__init__( - self, + self, "packet_decoder", gr.io_signature(1, 1, gr.sizeof_char), # Input signature gr.io_signature(1, 1, self._item_size_out) # Output signature @@ -183,12 +183,10 @@ class packet_decoder(gr.hier_block2): _packet_decoder_thread(self._msgq_in, self._recv_packet) def _recv_packet(self, ok, payload): - """! + """ Extract the payload from the packet and push onto message queue. @param ok boolean ok @param payload data received """ msg = gr.message_from_string(payload, 0, self._item_size_out, len(payload)/self._item_size_out) - if ok: self._msgq_out.insert_tail(msg) - - + if ok: self._msgq_out.insert_tail(msg) diff --git a/grc/src/grc_gnuradio/blks2/queue.py b/grc/src/grc_gnuradio/blks2/queue.py index cec35e52a..25ea1c616 100644 --- a/grc/src/grc_gnuradio/blks2/queue.py +++ b/grc/src/grc_gnuradio/blks2/queue.py @@ -1,37 +1,37 @@ # Copyright 2008 Free Software Foundation, Inc. -# +# # This file is part of GNU Radio -# +# # GNU Radio is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3, or (at your option) # any later version. -# +# # GNU Radio is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. -# +# # You should have received a copy of the GNU General Public License # along with GNU Radio; see the file COPYING. If not, write to # the Free Software Foundation, Inc., 51 Franklin Street, # Boston, MA 02110-1301, USA. -# +# from gnuradio import gr import gnuradio.gr.gr_threading as _threading import numpy ####################################################################################### -## Queue Sink Thread +## Queue Sink Thread ####################################################################################### class queue_sink_thread(_threading.Thread): - """! + """ Read samples from the queue sink and execute the callback. """ - + def __init__(self, queue_sink, callback): - """! + """ Queue sink thread contructor. @param queue_sink the queue to pop messages from @param callback the function of one argument @@ -42,31 +42,31 @@ class queue_sink_thread(_threading.Thread): self.setDaemon(1) self.keep_running = True self.start() - + def run(self): while self.keep_running: self._callback(self._queue_sink.pop()) ####################################################################################### -## Queue Sink +## Queue Sink ####################################################################################### class _queue_sink_base(gr.hier_block2): - """! + """ Queue sink base, a queue sink for any size queue. Easy read access to a gnuradio data stream from python. Call pop to read a sample from a gnuradio data stream. Samples are cast as python data types, complex, float, or int. """ - + def __init__(self, vlen=1): - """! + """ Queue sink base contructor. @param vlen the vector length """ self._vlen = vlen #initialize hier2 gr.hier_block2.__init__( - self, + self, "queue_sink", gr.io_signature(1, 1, self._item_size*self._vlen), # Input signature gr.io_signature(0, 0, 0) # Output signature @@ -77,9 +77,9 @@ class _queue_sink_base(gr.hier_block2): #connect self.connect(self, message_sink) self.arr = '' - + def pop(self): - """! + """ Pop a new sample off the front of the queue. @return a new sample """ @@ -95,59 +95,59 @@ class _queue_sink_base(gr.hier_block2): class queue_sink_c(_queue_sink_base): _item_size = gr.sizeof_gr_complex _numpy = numpy.complex64 - def _cast(self, arg): return complex(arg.real, arg.imag) - + def _cast(self, arg): return complex(arg.real, arg.imag) + class queue_sink_f(_queue_sink_base): _item_size = gr.sizeof_float _numpy = numpy.float32 _cast = float - + class queue_sink_i(_queue_sink_base): _item_size = gr.sizeof_int _numpy = numpy.int32 _cast = int - + class queue_sink_s(_queue_sink_base): _item_size = gr.sizeof_short _numpy = numpy.int16 _cast = int - + class queue_sink_b(_queue_sink_base): _item_size = gr.sizeof_char _numpy = numpy.int8 _cast = int - + ####################################################################################### -## Queue Source +## Queue Source ####################################################################################### class _queue_source_base(gr.hier_block2): - """! + """ Queue source base, a queue source for any size queue. Easy write access to a gnuradio data stream from python. Call push to to write a sample into the gnuradio data stream. """ - + def __init__(self, vlen=1): - """! + """ Queue source base contructor. @param vlen the vector length """ self._vlen = vlen #initialize hier2 gr.hier_block2.__init__( - self, + self, "queue_source", gr.io_signature(0, 0, 0), # Input signature gr.io_signature(1, 1, self._item_size*self._vlen) # Output signature ) #create message sink - message_source = gr.message_source(self._item_size*self._vlen, 1) + message_source = gr.message_source(self._item_size*self._vlen, 1) self._msgq = message_source.msgq() #connect self.connect(message_source, self) - + def push(self, item): - """! + """ Push an item into the back of the queue. @param item the item """ @@ -159,20 +159,19 @@ class _queue_source_base(gr.hier_block2): class queue_source_c(_queue_source_base): _item_size = gr.sizeof_gr_complex _numpy = numpy.complex64 - + class queue_source_f(_queue_source_base): _item_size = gr.sizeof_float _numpy = numpy.float32 - + class queue_source_i(_queue_source_base): _item_size = gr.sizeof_int _numpy = numpy.int32 - + class queue_source_s(_queue_source_base): _item_size = gr.sizeof_short _numpy = numpy.int16 - + class queue_source_b(_queue_source_base): _item_size = gr.sizeof_char _numpy = numpy.int8 - diff --git a/grc/src/grc_gnuradio/blks2/selector.py b/grc/src/grc_gnuradio/blks2/selector.py index 787f6547f..0997a5ce7 100644 --- a/grc/src/grc_gnuradio/blks2/selector.py +++ b/grc/src/grc_gnuradio/blks2/selector.py @@ -1,92 +1,92 @@ #!/usr/bin/env python # # Copyright 2008 Free Software Foundation, Inc. -# +# # This file is part of GNU Radio -# +# # GNU Radio is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3, or (at your option) # any later version. -# +# # GNU Radio is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. -# +# # You should have received a copy of the GNU General Public License # along with GNU Radio; see the file COPYING. If not, write to # the Free Software Foundation, Inc., 51 Franklin Street, # Boston, MA 02110-1301, USA. -# +# from gnuradio import gr - + class selector(gr.hier_block2): """A hier2 block with N inputs and M outputs, where data is only forwarded through input n to output m.""" - def __init__(self, item_size, num_inputs, num_outputs, input_index, output_index): - """! + def __init__(self, item_size, num_inputs, num_outputs, input_index, output_index): + """ SelectorHelper constructor. @param item_size the size of the gr data stream in bytes @param num_inputs the number of inputs (integer) @param num_outputs the number of outputs (integer) @param input_index the index for the source data @param output_index the index for the destination data - """ + """ gr.hier_block2.__init__( - self, 'selector', - gr.io_signature(num_inputs, num_inputs, item_size), + self, 'selector', + gr.io_signature(num_inputs, num_inputs, item_size), gr.io_signature(num_outputs, num_outputs, item_size), ) - #terminator blocks for unused inputs and outputs + #terminator blocks for unused inputs and outputs self.input_terminators = [gr.null_sink(item_size)] * num_inputs self.output_terminators = [gr.head(item_size, 0)] * num_outputs self.copy = None - #connections + #connections for i in range(num_inputs): self.connect((self, i), self.input_terminators[i]) - for i in range(num_outputs): self.connect(gr.null_source(item_size), self.output_terminators[i], (self, i)) - self.item_size = item_size + for i in range(num_outputs): self.connect(gr.null_source(item_size), self.output_terminators[i], (self, i)) + self.item_size = item_size self.input_index = input_index - self.output_index = output_index + self.output_index = output_index self.num_inputs = num_inputs self.num_outputs = num_outputs self._connect_current() - + def _indexes_valid(self): - """! + """ Are the input and output indexes within range of the number of inputs and outputs? @return true if input index and output index are in range """ return self.input_index in range(self.num_inputs) and self.output_index in range(self.num_outputs) - + def _connect_current(self): - """If the input and output indexes are valid: - disconnect the blocks at the input and output index from their terminators, + """If the input and output indexes are valid: + disconnect the blocks at the input and output index from their terminators, and connect them to one another. Then connect the terminators to one another.""" if self._indexes_valid(): - self.disconnect((self, self.input_index), self.input_terminators[self.input_index]) + self.disconnect((self, self.input_index), self.input_terminators[self.input_index]) self.disconnect(self.output_terminators[self.output_index], (self, self.output_index)) self.copy = gr.skiphead(self.item_size, 0) self.connect((self, self.input_index), self.copy) - self.connect(self.copy, (self, self.output_index)) - self.connect(self.output_terminators[self.output_index], self.input_terminators[self.input_index]) - + self.connect(self.copy, (self, self.output_index)) + self.connect(self.output_terminators[self.output_index], self.input_terminators[self.input_index]) + def _disconnect_current(self): - """If the input and output indexes are valid: - disconnect the blocks at the input and output index from one another, + """If the input and output indexes are valid: + disconnect the blocks at the input and output index from one another, and the terminators at the input and output index from one another. Reconnect the blocks to the terminators.""" if self._indexes_valid(): self.disconnect((self, self.input_index), self.copy) self.disconnect(self.copy, (self, self.output_index)) self.disconnect(self.output_terminators[self.output_index], self.input_terminators[self.input_index]) - del self.copy - self.copy = None + del self.copy + self.copy = None self.connect((self, self.input_index), self.input_terminators[self.input_index]) self.connect(self.output_terminators[self.output_index], (self, self.output_index)) - + def set_input_index(self, input_index): - """! + """ Change the block to the new input index if the index changed. @param input_index the new input index """ @@ -95,25 +95,25 @@ class selector(gr.hier_block2): self._disconnect_current() self.input_index = input_index self._connect_current() - self.unlock() - + self.unlock() + def set_output_index(self, output_index): - """! + """ Change the block to the new output index if the index changed. @param output_index the new output index - """ - if self.output_index != output_index: + """ + if self.output_index != output_index: self.lock() self._disconnect_current() self.output_index = output_index - self._connect_current() - self.unlock() + self._connect_current() + self.unlock() class valve(selector): """Wrapper for selector with 1 input and 1 output.""" - + def __init__(self, item_size, open): - """! + """ Constructor for valve. @param item_size the size of the gr data stream in bytes @param open true if initial valve state is open @@ -121,13 +121,12 @@ class valve(selector): if open: output_index = -1 else: output_index = 0 selector.__init__(self, item_size, 1, 1, 0, output_index) - + def set_open(self, open): - """! + """ Callback to set open state. @param open true to set valve state to open """ if open: output_index = -1 else: output_index = 0 self.set_output_index(output_index) - diff --git a/grc/src/grc_gnuradio/usrp/Makefile.am b/grc/src/grc_gnuradio/usrp/Makefile.am index 9689be8e0..5416ced41 100644 --- a/grc/src/grc_gnuradio/usrp/Makefile.am +++ b/grc/src/grc_gnuradio/usrp/Makefile.am @@ -19,9 +19,9 @@ # Boston, MA 02110-1301, USA. # -include $(top_srcdir)/Makefile.common +include $(top_srcdir)/grc/Makefile.inc -ourpythondir = $(pythondir)/grc_gnuradio/usrp +ourpythondir = $(grc_gnuradio_prefix)/usrp ourpython_PYTHON = \ __init__.py \ diff --git a/grc/src/grc_gnuradio/usrp/__init__.py b/grc/src/grc_gnuradio/usrp/__init__.py index 0962df14c..58e3b1dfc 100644 --- a/grc/src/grc_gnuradio/usrp/__init__.py +++ b/grc/src/grc_gnuradio/usrp/__init__.py @@ -1,25 +1,24 @@ # Copyright 2008 Free Software Foundation, Inc. -# +# # This file is part of GNU Radio -# +# # GNU Radio is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3, or (at your option) # any later version. -# +# # GNU Radio is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. -# +# # You should have received a copy of the GNU General Public License # along with GNU Radio; see the file COPYING. If not, write to # the Free Software Foundation, Inc., 51 Franklin Street, # Boston, MA 02110-1301, USA. -# +# from simple_usrp import simple_source_c, simple_source_s from simple_usrp import dual_source_c, dual_source_s from simple_usrp import simple_sink_c, simple_sink_s from simple_usrp import dual_sink_c, dual_sink_s - diff --git a/grc/src/grc_gnuradio/usrp/simple_usrp.py b/grc/src/grc_gnuradio/usrp/simple_usrp.py index 118ccc16a..dd33ef12b 100644 --- a/grc/src/grc_gnuradio/usrp/simple_usrp.py +++ b/grc/src/grc_gnuradio/usrp/simple_usrp.py @@ -22,11 +22,11 @@ import sys from gnuradio import usrp, gr #################################################################### -# Helper Functions +# Helper Functions #################################################################### def _set_frequency(u, which, subdev, frequency, verbose=False): - """! + """ Set the carrier frequency for the given subdevice. @param u the usrp source/sink @param which specifies the DDC/DUC number @@ -44,7 +44,7 @@ def _set_frequency(u, which, subdev, frequency, verbose=False): else: print >> sys.stderr, 'Error calling tune on subdevice.' def _setup_rx_subdev(u, subdev_spec, ddc, gain, frequency, auto_tr=None, rx_ant=None): - """! + """ Setup a usrp receive subdevice by setting gain and frequency. Add the gain and frequency callbacks to the flow graph. FlexRF: Handle auto transmit/receive and set the receive antenna. @@ -65,7 +65,7 @@ def _setup_rx_subdev(u, subdev_spec, ddc, gain, frequency, auto_tr=None, rx_ant= return subdev def _setup_tx_subdev(u, subdev_spec, gain, frequency, auto_tr=None, tx_enb=None): - """! + """ Setup a usrp receive subdevice by setting gain and frequency. Add the gain and frequency callbacks to the flow graph. FlexRF: Handle auto transmit/receive and enable the transmitter. @@ -94,7 +94,7 @@ constructor_to_size = { #################################################################### #################################################################### -# Simple USRP Base Classes +# Simple USRP Base Classes #################################################################### #################################################################### @@ -102,7 +102,7 @@ class _simple_usrp(object): """A single usrp source/sink base class.""" def __init__(self, u, subdev, which): - """! + """ Create a simple usrp base class. @param u the usrp object @param subdev the subdevice object @@ -113,41 +113,41 @@ class _simple_usrp(object): self._which = which def get_u(self): - """! + """ Get the underlying usrp object. @return the usrp source/sink object. """ return self._u def get_subdev(self): - """! + """ Get the underlying subdevice. @return the subdev object. """ return self._subdev def set_frequency(self, frequency): - """! + """ Set the frequency of the subdevice. @param frequency the frequency to tune """ _set_frequency(self.get_u(), self._which, self.get_subdev(), frequency) def set_gain(self, gain): - """! + """ Set the gain of the subdevice. @param gain the gain to set """ self.get_subdev().set_gain(gain) #################################################################### -# Simple USRP Source +# Simple USRP Source #################################################################### class _simple_source(gr.hier_block2, _simple_usrp): """A single usrp source of IO type short or complex.""" def __init__(self, number, subdev_spec, frequency, decimation, gain, mux=None, auto_tr=None, rx_ant=None): - """! + """ USRP simple source contructor. @param number the unit number @param subdev_spec the sub-device specification tuple @@ -181,13 +181,13 @@ class simple_source_c(_simple_source): constructor = usrp.source_c class simple_source_s(_simple_source): constructor = usrp.source_s #################################################################### -# Simple USRP Sink +# Simple USRP Sink #################################################################### class _simple_sink(gr.hier_block2, _simple_usrp): """A single usrp sink of IO type short or complex.""" def __init__(self, number, subdev_spec, frequency, interpolation, gain, mux=None, auto_tr=None, tx_enb=None): - """! + """ USRP simple sink contructor. @param number the unit number @param subdev_spec the sub-device specification tuple @@ -222,7 +222,7 @@ class simple_sink_s(_simple_sink): constructor = usrp.sink_s #################################################################### #################################################################### -# Dual USRP Base Classes +# Dual USRP Base Classes #################################################################### #################################################################### @@ -230,7 +230,7 @@ class _dual_usrp(object): """A dual usrp source/sink base class.""" def __init__(self, u, subdev_a, subdev_b, which_a, which_b): - """! + """ Create a dual usrp base class. @param u the usrp object @param subdev_a the subdevice object side a @@ -245,62 +245,62 @@ class _dual_usrp(object): self._which_b = which_b def get_u(self): - """! + """ Get the underlying usrp object. @return the usrp source/sink object. """ return self._u def get_subdev_a(self): - """! + """ Get the underlying subdevice. @return the subdev object. """ return self._subdev_a def get_subdev_b(self): - """! + """ Get the underlying subdevice. @return the subdev object. """ return self._subdev_b def set_frequency_a(self, frequency): - """! + """ Set the frequency of the subdevice. @param frequency the frequency to tune """ _set_frequency(self.get_u(), self._which_a, self.get_subdev_a(), frequency) def set_frequency_b(self, frequency): - """! + """ Set the frequency of the subdevice. @param frequency the frequency to tune """ _set_frequency(self.get_u(), self._which_b, self.get_subdev_b(), frequency) def set_gain_a(self, gain): - """! + """ Set the gain of the subdevice. @param gain the gain to set """ self.get_subdev_a().set_gain(gain) def set_gain_b(self, gain): - """! + """ Set the gain of the subdevice. @param gain the gain to set """ self.get_subdev_b().set_gain(gain) #################################################################### -# Dual USRP Source +# Dual USRP Source #################################################################### class _dual_source(gr.hier_block2, _dual_usrp): """A dual usrp source of IO type short or complex.""" def __init__(self, number, frequency_a, frequency_b, decimation, gain_a, gain_b, mux=0x3210, auto_tr=None, rx_ant_a=None, rx_ant_b=None): - """! + """ USRP dual source contructor. @param number the unit number @param frequency_a the frequency to tune side a @@ -337,13 +337,13 @@ class dual_source_c(_dual_source): constructor = usrp.source_c class dual_source_s(_dual_source): constructor = usrp.source_s #################################################################### -# Dual USRP Sink +# Dual USRP Sink #################################################################### class _dual_sink(gr.hier_block2, _dual_usrp): """A dual usrp sink of IO type short or complex.""" def __init__(self, number, frequency_a, frequency_b, interpolation, gain_a, gain_b, mux=0xba98, auto_tr=None, tx_enb_a=None, tx_enb_b=None): - """! + """ USRP dual sink contructor. @param number the unit number @param subdev_spec the sub-device specification tuple @@ -376,4 +376,3 @@ class _dual_sink(gr.hier_block2, _dual_usrp): class dual_sink_c(_dual_sink): constructor = usrp.sink_c class dual_sink_s(_dual_sink): constructor = usrp.sink_s - diff --git a/grc/src/grc_gnuradio/utils/__init__.py b/grc/src/grc_gnuradio/utils/__init__.py deleted file mode 100644 index 6cdfc263f..000000000 --- a/grc/src/grc_gnuradio/utils/__init__.py +++ /dev/null @@ -1,21 +0,0 @@ -""" -Copyright 2008 Free Software Foundation, Inc. -This file is part of GNU Radio - -GNU Radio Companion is free software; you can redistribute it and/or -modify it under the terms of the GNU General Public License -as published by the Free Software Foundation; either version 2 -of the License, or (at your option) any later version. - -GNU Radio Companion is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA -""" -##@package grc_gnuradio.utils -#utility functions and classes - diff --git a/grc/src/grc_gnuradio/wxgui/Makefile.am b/grc/src/grc_gnuradio/wxgui/Makefile.am index 2e7072eae..6f731f2cb 100644 --- a/grc/src/grc_gnuradio/wxgui/Makefile.am +++ b/grc/src/grc_gnuradio/wxgui/Makefile.am @@ -19,9 +19,9 @@ # Boston, MA 02110-1301, USA. # -include $(top_srcdir)/Makefile.common +include $(top_srcdir)/grc/Makefile.inc -ourpythondir = $(pythondir)/grc_gnuradio/wxgui +ourpythondir = $(grc_gnuradio_prefix)/wxgui ourpython_PYTHON = \ __init__.py \ diff --git a/grc/src/grc_gnuradio/wxgui/__init__.py b/grc/src/grc_gnuradio/wxgui/__init__.py index c0fdca52c..0b13ead9e 100644 --- a/grc/src/grc_gnuradio/wxgui/__init__.py +++ b/grc/src/grc_gnuradio/wxgui/__init__.py @@ -1,22 +1,22 @@ # Copyright 2008 Free Software Foundation, Inc. -# +# # This file is part of GNU Radio -# +# # GNU Radio is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 3, or (at your option) # any later version. -# +# # GNU Radio is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. -# +# # You should have received a copy of the GNU General Public License # along with GNU Radio; see the file COPYING. If not, write to # the Free Software Foundation, Inc., 51 Franklin Street, # Boston, MA 02110-1301, USA. -# +# from callback_controls import \ button_control, \ @@ -27,4 +27,3 @@ from callback_controls import \ slider_vertical_control, \ text_box_control from top_block_gui import top_block_gui - diff --git a/grc/src/grc_gnuradio/wxgui/callback_controls.py b/grc/src/grc_gnuradio/wxgui/callback_controls.py index c1ba784eb..2bb0b994e 100644 --- a/grc/src/grc_gnuradio/wxgui/callback_controls.py +++ b/grc/src/grc_gnuradio/wxgui/callback_controls.py @@ -48,7 +48,7 @@ class _chooser_control_base(_control_base): """House a drop down or radio buttons for variable control.""" def __init__(self, window, callback, label='Label', index=0, choices=[0], labels=[]): - """! + """ Chooser contructor. Create the slider, text box, and label. @param window the wx parent window @@ -68,14 +68,14 @@ class _chooser_control_base(_control_base): self._init() def _handle_changed(self, event=None): - """! + """ A change is detected. Call the callback. """ try: self.call() except Exception, e: print >> sys.stderr, 'Error in exec callback from handle changed.\n', e def get_value(self): - """! + """ Update the chooser. @return one of the possible choices """ @@ -83,7 +83,7 @@ class _chooser_control_base(_control_base): return self.choices[self.index] ############################################################################################## -# Button Control +# Button Control ############################################################################################## class button_control(_chooser_control_base): """House a button for variable control.""" @@ -98,7 +98,7 @@ class button_control(_chooser_control_base): self.button.SetLabel(self.labels[self.index]) ############################################################################################## -# Drop Down Control +# Drop Down Control ############################################################################################## class drop_down_control(_chooser_control_base): """House a drop down for variable control.""" @@ -113,7 +113,7 @@ class drop_down_control(_chooser_control_base): self.index = self.drop_down.GetSelection() ############################################################################################## -# Radio Buttons Control +# Radio Buttons Control ############################################################################################## class _radio_buttons_control_base(_chooser_control_base): """House radio buttons for variable control.""" @@ -147,13 +147,13 @@ class radio_buttons_vertical_control(_radio_buttons_control_base): radio_button_align = wx.ALIGN_LEFT ############################################################################################## -# Slider Control +# Slider Control ############################################################################################## class _slider_control_base(_control_base): """House a Slider and a Text Box for variable control.""" def __init__(self, window, callback, label='Label', value=50, min=0, max=100, num_steps=100): - """! + """ Slider contructor. Create the slider, text box, and label. @param window the wx parent window @@ -191,14 +191,14 @@ class _slider_control_base(_control_base): self.text_box.SetValue(str(self._value)) def get_value(self): - """! + """ Get the current set value. @return the value (float) """ return self._value def _set_slider_value(self, real_value): - """! + """ Translate the real numerical value into a slider value and, write the value to the slider. @param real_value the numeric value the slider should represent @@ -207,7 +207,7 @@ class _slider_control_base(_control_base): self.slider.SetValue(slider_value) def _handle_scroll(self, event=None): - """! + """ A scroll event is detected. Read the slider, call the callback. """ slider_value = self.slider.GetValue() @@ -218,7 +218,7 @@ class _slider_control_base(_control_base): except Exception, e: print >> sys.stderr, 'Error in exec callback from handle scroll.\n', e def _handle_enter(self, event=None): - """! + """ An enter key was pressed. Read the text box, call the callback. """ new_value = float(self.text_box.GetValue()) @@ -237,13 +237,13 @@ class slider_vertical_control(_slider_control_base): slider_size = 20, 200 ############################################################################################## -# Text Box Control +# Text Box Control ############################################################################################## class text_box_control(_control_base): """House a Text Box for variable control.""" def __init__(self, window, callback, label='Label', value=50): - """! + """ Text box contructor. Create the text box, and label. @param window the wx parent window @@ -264,14 +264,14 @@ class text_box_control(_control_base): self.text_box.SetValue(str(value)) def get_value(self): - """! + """ Get the current set value. @return the value (float) """ return self._value def _handle_enter(self, event=None): - """! + """ An enter key was pressed. Read the text box, call the callback. If the text cannot be evaluated, do not try callback. """ diff --git a/grc/src/grc_gnuradio/wxgui/top_block_gui.py b/grc/src/grc_gnuradio/wxgui/top_block_gui.py index d56d20056..fef9d18ce 100644 --- a/grc/src/grc_gnuradio/wxgui/top_block_gui.py +++ b/grc/src/grc_gnuradio/wxgui/top_block_gui.py @@ -28,7 +28,7 @@ class top_block_gui(gr.top_block): """gr top block with wx gui app and grid sizer.""" def __init__(self, title='', size=default_gui_size, icon=None): - """! + """ Initialize the gr top block. Create the wx gui elements. @param title the main window title @@ -48,21 +48,21 @@ class top_block_gui(gr.top_block): self._wx_vbox = wx.BoxSizer(wx.VERTICAL) def GetWin(self): - """! + """ Get the window for wx elements to fit within. @return the wx frame """ return self._wx_frame def Add(self, win): - """! + """ Add a window to the wx vbox. @param win the wx window """ self._wx_vbox.Add(win, 0, wx.EXPAND) def GridAdd(self, win, row, col, row_span=1, col_span=1): - """! + """ Add a window to the wx grid at the given position. @param win the wx window @param row the row specification (integer >= 0) @@ -73,7 +73,7 @@ class top_block_gui(gr.top_block): self._wx_grid.Add(win, wx.GBPosition(row, col), wx.GBSpan(row_span, col_span), wx.EXPAND) def Run(self): - """! + """ Setup the wx gui elements. Start the gr top block. Block with the wx main loop. @@ -96,4 +96,3 @@ class top_block_gui(gr.top_block): gr.top_block.start(self) #blocking main loop self._wx_app.MainLoop() - diff --git a/grc/src/grc/ActionHandler.py b/grc/src/gui/ActionHandler.py index ccaeb5709..ab4d66502 100644 --- a/grc/src/grc/ActionHandler.py +++ b/grc/src/gui/ActionHandler.py @@ -16,23 +16,24 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package ActionHandler -#ActionHandler builds the interface and handles most of the user inputs. import os import signal -from Constants import * -from Actions import * +from .. platforms.base.Constants import PY_GTK_ICON, IMAGE_FILE_EXTENSION +from Constants import DIR_LEFT, DIR_RIGHT +import Actions import pygtk pygtk.require('2.0') import gtk -import gui import Preferences from threading import Thread import Messages -import ParseXML +from .. utils import ParseXML import random -from grc.gui.elements.Platform import Platform +from .. platforms.gui.Platform import Platform +from MainWindow import MainWindow +from Dialogs import PreferencesDialog, AboutDialog, HotKeysDialog +from FileDialogs import OpenFlowGraphFileDialog, SaveFlowGraphFileDialog, SaveImageFileDialog class ActionHandler: """ @@ -41,7 +42,7 @@ class ActionHandler: """ def __init__(self, file_paths, platform): - """! + """ ActionHandler constructor. Create the main window, setup the message handler, import the preferences, and connect all of the action handlers. Finally, enter the gtk main loop and block. @@ -51,9 +52,9 @@ class ActionHandler: self.clipboard = None platform = Platform(platform) if PY_GTK_ICON: gtk.window_set_default_icon_from_file(PY_GTK_ICON) - for action in ACTIONS_LIST: action.connect('activate', self._handle_actions) + for action in Actions.ACTIONS_LIST: action.connect('activate', self._handle_actions) #setup the main window - self.main_window = gui.MainWindow(self.handle_states, platform) + self.main_window = MainWindow(self.handle_states, platform) self.main_window.connect('delete_event', self._quit) self.main_window.connect('key_press_event', self._handle_key_press) self.get_page = self.main_window.get_page @@ -64,7 +65,7 @@ class ActionHandler: Messages.send_init() #initialize self.init_file_paths = file_paths - self.handle_states(APPLICATION_INITIALIZE) + self.handle_states(Actions.APPLICATION_INITIALIZE) #enter the mainloop gtk.gdk.threads_init() gtk.main() @@ -83,71 +84,71 @@ class ActionHandler: shift = event.state & gtk.gdk.SHIFT_MASK #################### save/open/new/close ############################### if ctrl and keyname == 's': - self.handle_states(FLOW_GRAPH_SAVE) + self.handle_states(Actions.FLOW_GRAPH_SAVE) elif ctrl and keyname == 'o': - self.handle_states(FLOW_GRAPH_OPEN) + self.handle_states(Actions.FLOW_GRAPH_OPEN) elif ctrl and keyname == 'n': - self.handle_states(FLOW_GRAPH_NEW) + self.handle_states(Actions.FLOW_GRAPH_NEW) elif ctrl and keyname == 'q': - self.handle_states(FLOW_GRAPH_CLOSE) + self.handle_states(Actions.FLOW_GRAPH_CLOSE) #################### Cut/Copy/Paste ############################### elif self.get_focus_flag() and ctrl and keyname == 'x': #mouse focus - self.handle_states(BLOCK_CUT) + self.handle_states(Actions.BLOCK_CUT) elif self.get_focus_flag() and ctrl and keyname == 'c': #mouse focus - self.handle_states(BLOCK_COPY) + self.handle_states(Actions.BLOCK_COPY) elif self.get_focus_flag() and ctrl and keyname == 'v': #mouse focus - self.handle_states(BLOCK_PASTE) + self.handle_states(Actions.BLOCK_PASTE) #################### Undo/Redo ############################### elif ctrl and keyname == 'z': - self.handle_states(FLOW_GRAPH_UNDO) + self.handle_states(Actions.FLOW_GRAPH_UNDO) elif ctrl and keyname == 'y': - self.handle_states(FLOW_GRAPH_REDO) + self.handle_states(Actions.FLOW_GRAPH_REDO) #################### Delete ############################### elif self.get_focus_flag() and keyname == 'Delete': #mouse focus - self.handle_states(ELEMENT_DELETE) + self.handle_states(Actions.ELEMENT_DELETE) #################### Params ############################### elif self.get_focus_flag() and keyname == 'Return': #mouse focus - self.handle_states(BLOCK_PARAM_MODIFY) + self.handle_states(Actions.BLOCK_PARAM_MODIFY) #################### Rotate ############################### elif self.get_focus_flag() and keyname == 'Right': #mouse focus - self.handle_states(BLOCK_ROTATE_RIGHT) + self.handle_states(Actions.BLOCK_ROTATE_RIGHT) elif self.get_focus_flag() and keyname == 'Left': #mouse focus - self.handle_states(BLOCK_ROTATE_LEFT) + self.handle_states(Actions.BLOCK_ROTATE_LEFT) #################### Enable/Disable ############################### elif self.get_focus_flag() and keyname == 'e': #mouse focus - self.handle_states(BLOCK_ENABLE) + self.handle_states(Actions.BLOCK_ENABLE) elif self.get_focus_flag() and keyname == 'd': #mouse focus - self.handle_states(BLOCK_DISABLE) + self.handle_states(Actions.BLOCK_DISABLE) #################### Data Type ############################### elif self.get_focus_flag() and keyname == 'Down': #mouse focus - self.handle_states(BLOCK_INC_TYPE) + self.handle_states(Actions.BLOCK_INC_TYPE) elif self.get_focus_flag() and keyname == 'Up': #mouse focus - self.handle_states(BLOCK_DEC_TYPE) + self.handle_states(Actions.BLOCK_DEC_TYPE) #################### Port Controllers ############################### elif self.get_focus_flag() and keyname in ('equal','plus', 'KP_Add'): #mouse focus - self.handle_states(PORT_CONTROLLER_INC) + self.handle_states(Actions.PORT_CONTROLLER_INC) elif self.get_focus_flag() and keyname in ('minus', 'KP_Subtract'): #mouse focus - self.handle_states(PORT_CONTROLLER_DEC) + self.handle_states(Actions.PORT_CONTROLLER_DEC) #################### Gen/Exec/Stop/Print ############################### elif keyname == 'F5': - self.handle_states(FLOW_GRAPH_GEN) + self.handle_states(Actions.FLOW_GRAPH_GEN) elif keyname == 'F6': - self.handle_states(FLOW_GRAPH_EXEC) + self.handle_states(Actions.FLOW_GRAPH_EXEC) elif keyname == 'F7': - self.handle_states(FLOW_GRAPH_KILL) + self.handle_states(Actions.FLOW_GRAPH_KILL) elif keyname == 'Print': - self.handle_states(FLOW_GRAPH_SCREEN_CAPTURE) + self.handle_states(Actions.FLOW_GRAPH_SCREEN_CAPTURE) #propagate this if the fg is not in focus or nothing is selected return self.get_focus_flag() and self.get_flow_graph().is_selected() def _quit(self, window, event): - """! + """ Handle the delete event from the main window. Generated by pressing X to close, alt+f4, or right click+close. This method in turns calls the state handler to quit. @return true """ - self.handle_states(APPLICATION_QUIT) + self.handle_states(Actions.APPLICATION_QUIT) return True def _handle_actions(self, event): @@ -159,7 +160,7 @@ class ActionHandler: self.handle_states(event.get_name()) def handle_states(self, state=''): - """! + """ Handle the state changes in the GUI. Handle all of the state changes that arise from the action handler or other gui and inputs in the application. The state passed to the handle_states method is a string descriping @@ -169,158 +170,162 @@ class ActionHandler: @param state a string describing the state change """ #print state - ############################################################################################## + ################################################## # Initalize/Quit - ############################################################################################## - if state == APPLICATION_INITIALIZE: - for action in ACTIONS_LIST: action.set_sensitive(False) #set all actions disabled + ################################################## + if state == Actions.APPLICATION_INITIALIZE: + for action in Actions.ACTIONS_LIST: action.set_sensitive(False) #set all actions disabled # enable a select few actions for action in ( - APPLICATION_QUIT, FLOW_GRAPH_NEW, FLOW_GRAPH_OPEN, FLOW_GRAPH_SAVE_AS, FLOW_GRAPH_CLOSE, - ABOUT_WINDOW_DISPLAY, HOTKEYS_WINDOW_DISPLAY, - PREFS_WINDOW_DISPLAY, FLOW_GRAPH_SCREEN_CAPTURE, - ): get_action_from_name(action).set_sensitive(True) - if not self.init_file_paths and Preferences.restore_files(): self.init_file_paths = Preferences.files_open() + Actions.APPLICATION_QUIT, Actions.FLOW_GRAPH_NEW, + Actions.FLOW_GRAPH_OPEN, Actions.FLOW_GRAPH_SAVE_AS, + Actions.FLOW_GRAPH_CLOSE, Actions.ABOUT_WINDOW_DISPLAY, + Actions.HOTKEYS_WINDOW_DISPLAY, Actions.PREFS_WINDOW_DISPLAY, + Actions.FLOW_GRAPH_SCREEN_CAPTURE, + ): Actions.get_action_from_name(action).set_sensitive(True) + if not self.init_file_paths and Preferences.restore_files(): + self.init_file_paths = Preferences.files_open() if not self.init_file_paths: self.init_file_paths = [''] for file_path in self.init_file_paths: if file_path: self.main_window.new_page(file_path) #load pages from file paths - if Preferences.file_open() in self.init_file_paths: self.main_window.new_page(Preferences.file_open(), show=True) + if Preferences.file_open() in self.init_file_paths: + self.main_window.new_page(Preferences.file_open(), show=True) if not self.get_page(): self.main_window.new_page() #ensure that at least a blank page exists - elif state == APPLICATION_QUIT: + elif state == Actions.APPLICATION_QUIT: if self.main_window.close_pages(): gtk.main_quit() exit(0) - ############################################################################################## + ################################################## # Selections - ############################################################################################## - elif state == ELEMENT_SELECT: + ################################################## + elif state == Actions.ELEMENT_SELECT: self.get_flow_graph().update() - elif state == NOTHING_SELECT: + elif state == Actions.NOTHING_SELECT: self.get_flow_graph().unselect() self.get_flow_graph().update() - ############################################################################################## + ################################################## # Enable/Disable - ############################################################################################## - elif state == BLOCK_ENABLE: + ################################################## + elif state == Actions.BLOCK_ENABLE: if self.get_flow_graph().enable_selected(True): self.get_flow_graph().update() self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - elif state == BLOCK_DISABLE: + elif state == Actions.BLOCK_DISABLE: if self.get_flow_graph().enable_selected(False): self.get_flow_graph().update() self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - ############################################################################################## + ################################################## # Cut/Copy/Paste - ############################################################################################## - elif state == BLOCK_CUT: + ################################################## + elif state == Actions.BLOCK_CUT: self.handle_states(BLOCK_COPY) self.handle_states(ELEMENT_DELETE) - elif state == BLOCK_COPY: + elif state == Actions.BLOCK_COPY: self.clipboard = self.get_flow_graph().copy_to_clipboard() - elif state == BLOCK_PASTE: + elif state == Actions.BLOCK_PASTE: if self.clipboard: self.get_flow_graph().paste_from_clipboard(self.clipboard) self.get_flow_graph().update() self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - ############################################################################################## + ################################################## # Move/Rotate/Delete/Create - ############################################################################################## - elif state == BLOCK_MOVE: + ################################################## + elif state == Actions.BLOCK_MOVE: self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - elif state == BLOCK_ROTATE_LEFT: + elif state == Actions.BLOCK_ROTATE_LEFT: if self.get_flow_graph().rotate_selected(DIR_LEFT): self.get_flow_graph().update() self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - elif state == BLOCK_ROTATE_RIGHT: + elif state == Actions.BLOCK_ROTATE_RIGHT: if self.get_flow_graph().rotate_selected(DIR_RIGHT): self.get_flow_graph().update() self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - elif state == ELEMENT_DELETE: + elif state == Actions.ELEMENT_DELETE: if self.get_flow_graph().remove_selected(): self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) - self.handle_states(NOTHING_SELECT) + self.handle_states(Actions.NOTHING_SELECT) self.get_page().set_saved(False) - elif state == ELEMENT_CREATE: + elif state == Actions.ELEMENT_CREATE: self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) - self.handle_states(NOTHING_SELECT) + self.handle_states(Actions.NOTHING_SELECT) self.get_page().set_saved(False) - elif state == BLOCK_INC_TYPE: + elif state == Actions.BLOCK_INC_TYPE: if self.get_flow_graph().type_controller_modify_selected(1): self.get_flow_graph().update() self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - elif state == BLOCK_DEC_TYPE: + elif state == Actions.BLOCK_DEC_TYPE: if self.get_flow_graph().type_controller_modify_selected(-1): self.get_flow_graph().update() self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - elif state == PORT_CONTROLLER_INC: + elif state == Actions.PORT_CONTROLLER_INC: if self.get_flow_graph().port_controller_modify_selected(1): self.get_flow_graph().update() self.get_flow_graph().update() #2 times self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - elif state == PORT_CONTROLLER_DEC: + elif state == Actions.PORT_CONTROLLER_DEC: if self.get_flow_graph().port_controller_modify_selected(-1): self.get_flow_graph().update() self.get_flow_graph().update() #2 times self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - ############################################################################################## + ################################################## # Window stuff - ############################################################################################## - elif state == PREFS_WINDOW_DISPLAY: - gui.PreferencesDialog() + ################################################## + elif state == Actions.PREFS_WINDOW_DISPLAY: + PreferencesDialog() self.get_flow_graph().update() - elif state == ABOUT_WINDOW_DISPLAY: - gui.AboutDialog() - elif state == HOTKEYS_WINDOW_DISPLAY: - gui.HotKeysDialog() - ############################################################################################## + elif state == Actions.ABOUT_WINDOW_DISPLAY: + AboutDialog() + elif state == Actions.HOTKEYS_WINDOW_DISPLAY: + HotKeysDialog() + ################################################## # Param Modifications - ############################################################################################## - elif state == BLOCK_PARAM_MODIFY: + ################################################## + elif state == Actions.BLOCK_PARAM_MODIFY: if self.get_flow_graph().param_modify_selected(): self.get_flow_graph().update() self.get_page().get_state_cache().save_new_state(self.get_flow_graph().export_data()) self.get_page().set_saved(False) - ############################################################################################## + ################################################## # Undo/Redo - ############################################################################################## - elif state == FLOW_GRAPH_UNDO: + ################################################## + elif state == Actions.FLOW_GRAPH_UNDO: n = self.get_page().get_state_cache().get_prev_state() if n: self.get_flow_graph().unselect() self.get_flow_graph().import_data(n) self.get_flow_graph().update() self.get_page().set_saved(False) - elif state == FLOW_GRAPH_REDO: + elif state == Actions.FLOW_GRAPH_REDO: n = self.get_page().get_state_cache().get_next_state() if n: self.get_flow_graph().unselect() self.get_flow_graph().import_data(n) self.get_flow_graph().update() self.get_page().set_saved(False) - ############################################################################################## + ################################################## # New/Open/Save/Close - ############################################################################################## - elif state == FLOW_GRAPH_NEW: + ################################################## + elif state == Actions.FLOW_GRAPH_NEW: self.main_window.new_page() - elif state == FLOW_GRAPH_OPEN: - file_paths = gui.OpenFlowGraphFileDialog(self.get_page().get_file_path()).run() + elif state == Actions.FLOW_GRAPH_OPEN: + file_paths = OpenFlowGraphFileDialog(self.get_page().get_file_path()).run() if file_paths: #open a new page for each file, show only the first for i,file_path in enumerate(file_paths): self.main_window.new_page(file_path, show=(i==0)) - elif state == FLOW_GRAPH_CLOSE: + elif state == Actions.FLOW_GRAPH_CLOSE: self.main_window.close_page() - elif state == FLOW_GRAPH_SAVE: - if not self.get_page().get_file_path(): self.handle_states(FLOW_GRAPH_SAVE_AS) + elif state == Actions.FLOW_GRAPH_SAVE: + if not self.get_page().get_file_path(): self.handle_states(Actions.FLOW_GRAPH_SAVE_AS) else: try: ParseXML.to_file(self.get_flow_graph().export_data(), self.get_page().get_file_path()) @@ -328,26 +333,26 @@ class ActionHandler: except IOError: Messages.send_fail_save(self.get_page().get_file_path()) self.get_page().set_saved(False) - elif state == FLOW_GRAPH_SAVE_AS: - file_path = gui.SaveFlowGraphFileDialog(self.get_page().get_file_path()).run() + elif state == Actions.FLOW_GRAPH_SAVE_AS: + file_path = SaveFlowGraphFileDialog(self.get_page().get_file_path()).run() if file_path != None: self.get_page().set_file_path(file_path) - self.handle_states(FLOW_GRAPH_SAVE) - elif state == FLOW_GRAPH_SCREEN_CAPTURE: - file_path = gui.SaveImageFileDialog(self.get_page().get_file_path()).run() + self.handle_states(Actions.FLOW_GRAPH_SAVE) + elif state == Actions.FLOW_GRAPH_SCREEN_CAPTURE: + file_path = SaveImageFileDialog(self.get_page().get_file_path()).run() if file_path != None: pixmap = self.get_flow_graph().get_drawing_area().pixmap width, height = pixmap.get_size() pixbuf = gtk.gdk.Pixbuf(gtk.gdk.COLORSPACE_RGB, 0, 8, width, height) pixbuf.get_from_drawable(pixmap, pixmap.get_colormap(), 0, 0, 0, 0, width, height) pixbuf.save(file_path, IMAGE_FILE_EXTENSION[1:]) - ############################################################################################## + ################################################## # Gen/Exec/Stop - ############################################################################################## - elif state == FLOW_GRAPH_GEN: + ################################################## + elif state == Actions.FLOW_GRAPH_GEN: if not self.get_page().get_pid(): if not self.get_page().get_saved() or not self.get_page().get_file_path(): - self.handle_states(FLOW_GRAPH_SAVE) #only save if file path missing or not saved + self.handle_states(Actions.FLOW_GRAPH_SAVE) #only save if file path missing or not saved if self.get_page().get_saved() and self.get_page().get_file_path(): generator = self.get_page().get_generator() try: @@ -355,37 +360,37 @@ class ActionHandler: generator.write() except Exception,e: Messages.send_fail_gen(e) else: self.generator = None - elif state == FLOW_GRAPH_EXEC: + elif state == Actions.FLOW_GRAPH_EXEC: if not self.get_page().get_pid(): - self.handle_states(FLOW_GRAPH_GEN) + self.handle_states(Actions.FLOW_GRAPH_GEN) if self.get_page().get_saved() and self.get_page().get_file_path(): ExecFlowGraphThread(self) - elif state == FLOW_GRAPH_KILL: + elif state == Actions.FLOW_GRAPH_KILL: if self.get_page().get_pid(): try: os.kill(self.get_page().get_pid(), signal.SIGKILL) except: print "could not kill pid: %s"%self.get_page().get_pid() elif state == '': #pass and run the global actions pass else: print '!!! State "%s" not handled !!!'%state - ############################################################################################## + ################################################## # Global Actions for all States - ############################################################################################## + ################################################## #update general buttons - get_action_from_name(ELEMENT_DELETE).set_sensitive(bool(self.get_flow_graph().get_selected_elements())) - get_action_from_name(BLOCK_PARAM_MODIFY).set_sensitive(bool(self.get_flow_graph().get_selected_block())) - get_action_from_name(BLOCK_ROTATE_RIGHT).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) - get_action_from_name(BLOCK_ROTATE_LEFT).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) + Actions.get_action_from_name(Actions.ELEMENT_DELETE).set_sensitive(bool(self.get_flow_graph().get_selected_elements())) + Actions.get_action_from_name(Actions.BLOCK_PARAM_MODIFY).set_sensitive(bool(self.get_flow_graph().get_selected_block())) + Actions.get_action_from_name(Actions.BLOCK_ROTATE_RIGHT).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) + Actions.get_action_from_name(Actions.BLOCK_ROTATE_LEFT).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) #update cut/copy/paste - get_action_from_name(BLOCK_CUT).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) - get_action_from_name(BLOCK_COPY).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) - get_action_from_name(BLOCK_PASTE).set_sensitive(bool(self.clipboard)) + Actions.get_action_from_name(Actions.BLOCK_CUT).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) + Actions.get_action_from_name(Actions.BLOCK_COPY).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) + Actions.get_action_from_name(Actions.BLOCK_PASTE).set_sensitive(bool(self.clipboard)) #update enable/disable - get_action_from_name(BLOCK_ENABLE).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) - get_action_from_name(BLOCK_DISABLE).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) + Actions.get_action_from_name(Actions.BLOCK_ENABLE).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) + Actions.get_action_from_name(Actions.BLOCK_DISABLE).set_sensitive(bool(self.get_flow_graph().get_selected_blocks())) #set the exec and stop buttons self.update_exec_stop() #saved status - get_action_from_name(FLOW_GRAPH_SAVE).set_sensitive(not self.get_page().get_saved()) + Actions.get_action_from_name(Actions.FLOW_GRAPH_SAVE).set_sensitive(not self.get_page().get_saved()) self.main_window.update() #draw the flow graph self.get_flow_graph().draw() @@ -396,14 +401,14 @@ class ActionHandler: Lock and unlock the mutex for race conditions with exec flow graph threads. """ sensitive = self.get_flow_graph().is_valid() and not self.get_page().get_pid() - get_action_from_name(FLOW_GRAPH_GEN).set_sensitive(sensitive) - get_action_from_name(FLOW_GRAPH_EXEC).set_sensitive(sensitive) - get_action_from_name(FLOW_GRAPH_KILL).set_sensitive(self.get_page().get_pid() != None) + Actions.get_action_from_name(Actions.FLOW_GRAPH_GEN).set_sensitive(sensitive) + Actions.get_action_from_name(Actions.FLOW_GRAPH_EXEC).set_sensitive(sensitive) + Actions.get_action_from_name(Actions.FLOW_GRAPH_KILL).set_sensitive(self.get_page().get_pid() != None) class ExecFlowGraphThread(Thread): """Execute the flow graph as a new process and wait on it to finish.""" def __init__ (self, action_handler): - """! + """ ExecFlowGraphThread constructor. @param action_handler an instance of an ActionHandler """ @@ -438,4 +443,3 @@ class ExecFlowGraphThread(Thread): self.page.set_pid(None) self.update_exec_stop() gtk.gdk.threads_leave() - diff --git a/grc/src/grc/Actions.py b/grc/src/gui/Actions.py index ebf10c7e1..ddd2573a8 100644 --- a/grc/src/grc/Actions.py +++ b/grc/src/gui/Actions.py @@ -16,9 +16,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package Actions -#Global actions for gui elements to communicate state changes to the action handler. -#Use gtk.stock_list_ids() to get a list of possible stock ids (for toolbar/menu icons) import pygtk pygtk.require('2.0') @@ -95,7 +92,7 @@ ACTIONS_LIST = ( ACTIONS_DICT = dict((action.get_name(), action) for action in ACTIONS_LIST) def get_action_from_name(action_name): - """! + """ Retrieve the action from the action list. Search the list and find an action with said name. @param action_name the action name(string) @@ -104,4 +101,3 @@ def get_action_from_name(action_name): """ if ACTIONS_DICT.has_key(action_name): return ACTIONS_DICT[action_name] raise KeyError('Action Name: "%s" does not exist'%action_name) - diff --git a/grc/src/grc/gui/Bars.py b/grc/src/gui/Bars.py index 00238b064..915e5abec 100644 --- a/grc/src/grc/gui/Bars.py +++ b/grc/src/gui/Bars.py @@ -16,84 +16,82 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.Bars -#Create the GUI's toolbar and menubar -from grc.Actions import * +import Actions import pygtk pygtk.require('2.0') import gtk ##The list of actions for the toolbar. TOOLBAR_LIST = ( - FLOW_GRAPH_NEW, - FLOW_GRAPH_OPEN, - FLOW_GRAPH_SAVE, - FLOW_GRAPH_CLOSE, + Actions.FLOW_GRAPH_NEW, + Actions.FLOW_GRAPH_OPEN, + Actions.FLOW_GRAPH_SAVE, + Actions.FLOW_GRAPH_CLOSE, None, - FLOW_GRAPH_SCREEN_CAPTURE, + Actions.FLOW_GRAPH_SCREEN_CAPTURE, None, - BLOCK_CUT, - BLOCK_COPY, - BLOCK_PASTE, - ELEMENT_DELETE, + Actions.BLOCK_CUT, + Actions.BLOCK_COPY, + Actions.BLOCK_PASTE, + Actions.ELEMENT_DELETE, None, - FLOW_GRAPH_UNDO, - FLOW_GRAPH_REDO, + Actions.FLOW_GRAPH_UNDO, + Actions.FLOW_GRAPH_REDO, None, - FLOW_GRAPH_GEN, - FLOW_GRAPH_EXEC, - FLOW_GRAPH_KILL, + Actions.FLOW_GRAPH_GEN, + Actions.FLOW_GRAPH_EXEC, + Actions.FLOW_GRAPH_KILL, None, - BLOCK_ROTATE_LEFT, - BLOCK_ROTATE_RIGHT, + Actions.BLOCK_ROTATE_LEFT, + Actions.BLOCK_ROTATE_RIGHT, None, - BLOCK_ENABLE, - BLOCK_DISABLE, + Actions.BLOCK_ENABLE, + Actions.BLOCK_DISABLE, ) ##The list of actions and categories for the menu bar. MENU_BAR_LIST = ( (gtk.Action('File', '_File', None, None), [ - FLOW_GRAPH_NEW, - FLOW_GRAPH_OPEN, + Actions.FLOW_GRAPH_NEW, + Actions.FLOW_GRAPH_OPEN, None, - FLOW_GRAPH_SAVE, - FLOW_GRAPH_SAVE_AS, + Actions.FLOW_GRAPH_SAVE, + Actions.FLOW_GRAPH_SAVE_AS, None, - FLOW_GRAPH_SCREEN_CAPTURE, + Actions.FLOW_GRAPH_SCREEN_CAPTURE, None, - FLOW_GRAPH_CLOSE, - APPLICATION_QUIT, + Actions.FLOW_GRAPH_CLOSE, + Actions.APPLICATION_QUIT, ]), (gtk.Action('Edit', '_Edit', None, None), [ - FLOW_GRAPH_UNDO, - FLOW_GRAPH_REDO, + Actions.FLOW_GRAPH_UNDO, + Actions.FLOW_GRAPH_REDO, None, - BLOCK_CUT, - BLOCK_COPY, - BLOCK_PASTE, - ELEMENT_DELETE, + Actions.BLOCK_CUT, + Actions.BLOCK_COPY, + Actions.BLOCK_PASTE, + Actions.ELEMENT_DELETE, None, - BLOCK_ROTATE_LEFT, - BLOCK_ROTATE_RIGHT, + Actions.BLOCK_ROTATE_LEFT, + Actions.BLOCK_ROTATE_RIGHT, None, - BLOCK_ENABLE, - BLOCK_DISABLE, + Actions.BLOCK_ENABLE, + Actions.BLOCK_DISABLE, None, - BLOCK_PARAM_MODIFY, + Actions.BLOCK_PARAM_MODIFY, ]), (gtk.Action('Build', '_Build', None, None), [ - FLOW_GRAPH_GEN, - FLOW_GRAPH_EXEC, - FLOW_GRAPH_KILL, + Actions.FLOW_GRAPH_GEN, + Actions.FLOW_GRAPH_EXEC, + Actions.FLOW_GRAPH_KILL, ]), (gtk.Action('Options', '_Options', None, None), [ - PREFS_WINDOW_DISPLAY, + Actions.PREFS_WINDOW_DISPLAY, ]), (gtk.Action('Help', '_Help', None, None), [ - ABOUT_WINDOW_DISPLAY, - HOTKEYS_WINDOW_DISPLAY, + Actions.ABOUT_WINDOW_DISPLAY, + Actions.HOTKEYS_WINDOW_DISPLAY, ]), ) @@ -109,7 +107,7 @@ class Toolbar(gtk.Toolbar): self.set_style(gtk.TOOLBAR_ICONS) for action_name in TOOLBAR_LIST: if action_name: #add a tool item - action = get_action_from_name(action_name) + action = Actions.get_action_from_name(action_name) self.add(action.create_tool_item()) #this reset of the tooltip property is required (after creating the tool item) for the tooltip to show action.set_property('tooltip', action.get_property('tooltip')) @@ -135,8 +133,7 @@ class MenuBar(gtk.MenuBar): main_menu_item.set_submenu(main_menu) for action_name in action_names: if action_name: #append a menu item - action = get_action_from_name(action_name) + action = Actions.get_action_from_name(action_name) main_menu.append(action.create_menu_item()) else: main_menu.append(gtk.SeparatorMenuItem()) main_menu.show_all() #this show all is required for the separators to show - diff --git a/grc/src/grc/gui/BlockTreeWindow.py b/grc/src/gui/BlockTreeWindow.py index 9543fdda2..291cc6f3b 100644 --- a/grc/src/grc/gui/BlockTreeWindow.py +++ b/grc/src/gui/BlockTreeWindow.py @@ -16,10 +16,8 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.BlockTreeWindow -#The block selection panel gives the user a tree selection to choose a block. -from grc.Constants import * +from Constants import BLOCK_SELECTION_WINDOW_WIDTH import pygtk pygtk.require('2.0') import gtk @@ -32,7 +30,7 @@ class BlockTreeWindow(gtk.VBox): """The block selection panel.""" def __init__(self, platform, get_flow_graph): - """! + """ BlockTreeWindow constructor. Create a tree view of the possible blocks in the platform. The tree view nodes will be category names, the leaves will be block names. @@ -77,7 +75,7 @@ class BlockTreeWindow(gtk.VBox): ## Block Tree Methods ############################################################ def add_block(self, category, block=None): - """! + """ Add a block with category to this selection window. Add only the category when block is None. @param category the category string @@ -103,7 +101,7 @@ class BlockTreeWindow(gtk.VBox): ## Helper Methods ############################################################ def _get_selected_block_key(self): - """! + """ Get the currently selected block key. @return the key of the selected block or a empty string """ @@ -112,7 +110,7 @@ class BlockTreeWindow(gtk.VBox): return iter and treestore.get_value(iter, KEY_INDEX) or '' def _update_add_button(self): - """! + """ Update the add button's sensitivity. The button should be active only if a block is selected. """ @@ -120,7 +118,7 @@ class BlockTreeWindow(gtk.VBox): self.add_button.set_sensitive(bool(key)) def _add_selected_block(self): - """! + """ Add the selected block with the given key to the flow graph. """ key = self._get_selected_block_key() @@ -130,7 +128,7 @@ class BlockTreeWindow(gtk.VBox): ## Event Handlers ############################################################ def _handle_mouse_button_press(self, widget, event): - """! + """ Handle the mouse button press. If a left double click is detected, call add selected block. """ @@ -138,16 +136,15 @@ class BlockTreeWindow(gtk.VBox): self._add_selected_block() def _handle_selection_change(self, selection): - """! + """ Handle a selection change in the tree view. If a selection changes, set the add button sensitive. """ self._update_add_button() def _handle_add_button(self, widget): - """! + """ Handle the add button clicked signal. Call add selected block. """ self._add_selected_block() - diff --git a/grc/src/gui/Constants.py b/grc/src/gui/Constants.py new file mode 100644 index 000000000..2f6af9a1f --- /dev/null +++ b/grc/src/gui/Constants.py @@ -0,0 +1,82 @@ +""" +Copyright 2008 Free Software Foundation, Inc. +This file is part of GNU Radio + +GNU Radio Companion is free software; you can redistribute it and/or +modify it under the terms of the GNU General Public License +as published by the Free Software Foundation; either version 2 +of the License, or (at your option) any later version. + +GNU Radio Companion is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program; if not, write to the Free Software +Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA +""" + +################################################## +## Global Titles +################################################## + +##The name to appear in the main window for a flow graph that has not been saved to file. +NEW_FLOGRAPH_TITLE = 'untitled' + +##The prefix title on the main window. +MAIN_WINDOW_PREFIX = "GRC" + +################################################## +## Signal block rotations +################################################## + +##direction of rotation left. +DIR_LEFT = 'left' + +##direction of rotation right. +DIR_RIGHT = 'right' + +################################################## +## Dimension constraints for the various windows (in pixels) +################################################## + +##main window constraints +MIN_WINDOW_WIDTH = 600 +MIN_WINDOW_HEIGHT = 400 + +##dialog constraints +MIN_DIALOG_WIDTH = 500 +MIN_DIALOG_HEIGHT = 500 + +##static height of reports window +REPORTS_WINDOW_HEIGHT = 100 + +##static width of block selection window +BLOCK_SELECTION_WINDOW_WIDTH = 200 + +################################################## +## Dragging, scrolling, and redrawing constants for the flow graph window in pixels +################################################## + +##How close can the mouse get to the window border before mouse events are ignored. +BORDER_PROXIMITY_SENSITIVITY = 50 + +##How close the mouse can get to the edge of the visible window before scrolling is invoked. +SCROLL_PROXIMITY_SENSITIVITY = 30 + +##When the window has to be scrolled, move it this distance in the required direction. +SCROLL_DISTANCE = 15 + +##The redrawing sensitivity, how many seconds must pass between motion events before a redraw? +MOTION_DETECT_REDRAWING_SENSITIVITY = .02 + +##How close the mouse click can be to a connection and register a connection select. +CONNECTION_SELECT_SENSITIVITY = 5 + +################################################## +# A state is recorded for each change to the flow graph, the size dictates how many states we can record +################################################## + +##The size of the state saving cache in the flow graph (for undo/redo functionality) +STATE_CACHE_SIZE = 42 diff --git a/grc/src/grc/gui/Dialogs.py b/grc/src/gui/Dialogs.py index 55e26846b..f7ba2954b 100644 --- a/grc/src/grc/gui/Dialogs.py +++ b/grc/src/gui/Dialogs.py @@ -16,20 +16,21 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.Dialogs -#Misc dialogs. import pygtk pygtk.require('2.0') import gtk -from grc.Constants import * -from grc import Preferences +from Constants import \ + MIN_DIALOG_WIDTH, MIN_DIALOG_HEIGHT, \ + MAIN_WINDOW_PREFIX +from .. platforms.base.Constants import VERSION +import Preferences class TextDisplay(gtk.TextView): """A non editable gtk text view.""" def __init__(self, text=''): - """! + """ TextDisplay constructor. @param text the text to display (string) """ @@ -42,7 +43,6 @@ class TextDisplay(gtk.TextView): self.set_cursor_visible(False) self.set_wrap_mode(gtk.WRAP_WORD_CHAR) -###################################################################################################### class PreferencesDialog(gtk.Dialog): """A dialog box to display the preferences.""" @@ -64,12 +64,12 @@ class PreferencesDialog(gtk.Dialog): self.run() self.destroy() -###################################################################################################### def MessageDialogHelper(type, buttons, title=None, markup=None): - """! + """ Create a modal message dialog and run it. @param type the type of message: gtk.MESSAGE_INFO, gtk.MESSAGE_WARNING, gtk.MESSAGE_QUESTION or gtk.MESSAGE_ERROR - @param buttons the predefined set of buttons to use: gtk.BUTTONS_NONE, gtk.BUTTONS_OK, gtk.BUTTONS_CLOSE, gtk.BUTTONS_CANCEL, gtk.BUTTONS_YES_NO, gtk.BUTTONS_OK_CANCEL + @param buttons the predefined set of buttons to use: + gtk.BUTTONS_NONE, gtk.BUTTONS_OK, gtk.BUTTONS_CLOSE, gtk.BUTTONS_CANCEL, gtk.BUTTONS_YES_NO, gtk.BUTTONS_OK_CANCEL @param tittle the title of the window (string) @param markup the message text with pango markup @return the gtk response from run() @@ -81,7 +81,6 @@ def MessageDialogHelper(type, buttons, title=None, markup=None): message_dialog.destroy() return response -###################################################################################################### class AboutDialog(gtk.AboutDialog): """A cute little about dialog.""" @@ -106,7 +105,6 @@ Achilleas Anastasopoulos -> trellis support self.run() self.destroy() -###################################################################################################### class HotKeysDialog(gtk.Dialog): """Display each action with the associated hotkey.""" diff --git a/grc/src/grc/gui/DrawingArea.py b/grc/src/gui/DrawingArea.py index 9100476a4..3588e122d 100644 --- a/grc/src/grc/gui/DrawingArea.py +++ b/grc/src/gui/DrawingArea.py @@ -16,13 +16,11 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.DrawingArea -#Drawing area for graphical elements. import pygtk pygtk.require('2.0') import gtk -from grc.Constants import * +from Constants import MIN_WINDOW_WIDTH, MIN_WINDOW_HEIGHT class DrawingArea(gtk.DrawingArea): """ @@ -31,7 +29,7 @@ class DrawingArea(gtk.DrawingArea): """ def __init__(self, main_window): - """! + """ DrawingArea contructor. Connect event handlers. @param main_window the main_window containing all flow graphs @@ -63,7 +61,7 @@ class DrawingArea(gtk.DrawingArea): self.gc = None def draw(self): - """! + """ Draw the pixmap onto this drawing area. """ self.window.draw_drawable(self.gc, self.pixmap, 0, 0, 0, 0, -1, -1) @@ -76,7 +74,7 @@ class DrawingArea(gtk.DrawingArea): self._focus_flag = focus_flag def _handle_mouse_button_press(self, widget, event): - """! + """ Forward button click information to the flow graph. """ self.ctrl_mask = event.state & gtk.gdk.CONTROL_MASK @@ -88,7 +86,7 @@ class DrawingArea(gtk.DrawingArea): return True def _handle_mouse_button_release(self, widget, event): - """! + """ Forward button release information to the flow graph. """ self.ctrl_mask = event.state & gtk.gdk.CONTROL_MASK @@ -99,7 +97,7 @@ class DrawingArea(gtk.DrawingArea): return True def _handle_mouse_motion(self, widget, event): - """! + """ Forward mouse motion information to the flow graph. """ self.ctrl_mask = event.state & gtk.gdk.CONTROL_MASK @@ -109,7 +107,7 @@ class DrawingArea(gtk.DrawingArea): return True def _handle_window_expose(self, widget, event): - """! + """ Called when the window initially appears or is resized: create a new pixmap, draw the flow graph. """ self.gc = self.window.new_gc() diff --git a/grc/src/grc/gui/FileDialogs.py b/grc/src/gui/FileDialogs.py index 62024710a..320c1161c 100644 --- a/grc/src/grc/gui/FileDialogs.py +++ b/grc/src/gui/FileDialogs.py @@ -16,14 +16,15 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.FileDialogs -#The open/save dialog for flow graph fFileDialogiles and screen shots. import pygtk pygtk.require('2.0') import gtk from Dialogs import MessageDialogHelper -from grc.Constants import DEFAULT_FILE_PATH,FLOW_GRAPH_FILE_EXTENSION,IMAGE_FILE_EXTENSION,NEW_FLOGRAPH_TITLE +from Constants import NEW_FLOGRAPH_TITLE +from .. platforms.base.Constants import \ + DEFAULT_FILE_PATH, FLOW_GRAPH_FILE_EXTENSION, \ + IMAGE_FILE_EXTENSION from os import path OPEN_FLOW_GRAPH = 'open flow graph' @@ -53,7 +54,7 @@ class FileDialogHelper(gtk.FileChooserDialog): """ def __init__(self, action, title): - """! + """ FileDialogHelper contructor. Create a save or open dialog with cancel and ok buttons. Use standard settings: no multiple selection, local files only, and the * filter. @@ -70,7 +71,7 @@ class FileDialog(FileDialogHelper): """A dialog box to save or open flow graph files. This is a base class, do not use.""" def __init__(self, current_file_path=''): - """! + """ FileDialog constructor. @param current_file_path the current directory or path to the open flow graph """ @@ -91,7 +92,7 @@ class FileDialog(FileDialogHelper): self.set_current_folder(path.dirname(current_file_path)) #current directory def add_and_set_filter(self, filter): - """! + """ Add the gtk file filter to the list of filters and set it as the default file filter. @param filter a gtk file filter. """ @@ -99,7 +100,7 @@ class FileDialog(FileDialogHelper): self.set_filter(filter) def get_rectified_filename(self): - """! + """ Run the dialog and get the filename. If this is a save dialog and the file name is missing the extension, append the file extension. If the file name with the extension already exists, show a overwrite dialog. @@ -140,7 +141,7 @@ class FileDialog(FileDialogHelper): return filenames def run(self): - """! + """ Get the filename and destroy the dialog. @return the filename or None if a close/cancel occured. """ @@ -151,4 +152,3 @@ class FileDialog(FileDialogHelper): class OpenFlowGraphFileDialog(FileDialog): type = OPEN_FLOW_GRAPH class SaveFlowGraphFileDialog(FileDialog): type = SAVE_FLOW_GRAPH class SaveImageFileDialog(FileDialog): type = SAVE_IMAGE - diff --git a/grc/src/grc/gui/MainWindow.py b/grc/src/gui/MainWindow.py index 6aafe66c1..e4c60fce5 100644 --- a/grc/src/grc/gui/MainWindow.py +++ b/grc/src/gui/MainWindow.py @@ -16,21 +16,23 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.MainWindow -#The main window, containing all windows, tool bars, and menu bars. -from grc.Constants import * -from grc.Actions import * +from Constants import \ + MIN_WINDOW_WIDTH, MIN_WINDOW_HEIGHT, \ + NEW_FLOGRAPH_TITLE, MAIN_WINDOW_PREFIX, \ + REPORTS_WINDOW_HEIGHT +from .. platforms.base.Constants import FLOW_GRAPH_FILE_EXTENSION +from Actions import APPLICATION_QUIT, FLOW_GRAPH_KILL import pygtk pygtk.require('2.0') import gtk import Bars from BlockTreeWindow import BlockTreeWindow -from Dialogs import TextDisplay,MessageDialogHelper +from Dialogs import TextDisplay, MessageDialogHelper from DrawingArea import DrawingArea -from grc import Preferences -from grc import Messages -from NotebookPage import Page +from NotebookPage import NotebookPage +import Preferences +import Messages import os ############################################################ @@ -41,7 +43,7 @@ class MainWindow(gtk.Window): """The topmost window with menus, the tool bar, and other major windows.""" def __init__(self, handle_states, platform): - """! + """ MainWindow contructor. @param handle_states the callback function """ @@ -99,7 +101,7 @@ class MainWindow(gtk.Window): ############################################################ def _quit(self, window, event): - """! + """ Handle the delete event from the main window. Generated by pressing X to close, alt+f4, or right click+close. This method in turns calls the state handler to quit. @@ -109,7 +111,7 @@ class MainWindow(gtk.Window): return True def _handle_page_change(self, notebook, page, page_num): - """! + """ Handle a page change. When the user clicks on a new tab, reload the flow graph to update the vars window and call handle states (select nothing) to update the buttons. @@ -126,7 +128,7 @@ class MainWindow(gtk.Window): ############################################################ def add_report_line(self, line): - """! + """ Place line at the end of the text buffer, then scroll its window all the way down. @param line the new text """ @@ -136,7 +138,7 @@ class MainWindow(gtk.Window): vadj.emit('changed') def _show_reports_window(self, show): - """! + """ Show the reports window when show is True. Hide the reports window when show is False. @param show boolean flag @@ -149,7 +151,7 @@ class MainWindow(gtk.Window): ############################################################ def new_page(self, file_path='', show=False): - """! + """ Create a new notebook page. Set the tab to be selected. @param file_path optional file to load into the flow graph @@ -166,7 +168,7 @@ class MainWindow(gtk.Window): #inject drawing area and handle states into flow graph flow_graph.drawing_area = self.drawing_area flow_graph.handle_states = self.handle_states - page = Page( + page = NotebookPage( self, flow_graph=flow_graph, file_path=file_path, @@ -231,7 +233,7 @@ class MainWindow(gtk.Window): ############################################################ def update(self): - """! + """ Set the title of the main window. Set the titles on the page tabs. Show/hide the reports window. @@ -251,10 +253,10 @@ class MainWindow(gtk.Window): for page in self._get_pages(): title = os.path.basename(page.get_file_path()) #strip file extension #TEMP - if title.endswith('.xml'): + if title.endswith('.xml'): title = title[0:-len('.xml')] #strip file extension - if title.endswith(FLOW_GRAPH_FILE_EXTENSION): + if title.endswith(FLOW_GRAPH_FILE_EXTENSION): title = title[0:-len(FLOW_GRAPH_FILE_EXTENSION)] page.set_text(''.join(( (title or NEW_FLOGRAPH_TITLE), @@ -269,14 +271,14 @@ class MainWindow(gtk.Window): else: self.notebook.hide() def get_page(self): - """! + """ Get the selected page. @return the selected page """ return self.current_page def get_flow_graph(self): - """! + """ Get the selected flow graph. @return the selected flow graph """ @@ -287,7 +289,7 @@ class MainWindow(gtk.Window): ############################################################ def _set_page(self, page): - """! + """ Set the current page. @param page the page widget """ @@ -295,7 +297,7 @@ class MainWindow(gtk.Window): self.notebook.set_current_page(self.notebook.page_num(self.current_page)) def _save_changes(self): - """! + """ Save changes to flow graph? @return true if yes """ @@ -317,4 +319,3 @@ class MainWindow(gtk.Window): @return list of pages """ return [self.notebook.get_nth_page(page_num) for page_num in range(self.notebook.get_n_pages())] - diff --git a/grc/src/grc/gui/Makefile.am b/grc/src/gui/Makefile.am index c9069beac..a6639af44 100644 --- a/grc/src/grc/gui/Makefile.am +++ b/grc/src/gui/Makefile.am @@ -19,19 +19,23 @@ # Boston, MA 02110-1301, USA. # -include $(top_srcdir)/Makefile.common +include $(top_srcdir)/grc/Makefile.inc -SUBDIRS = elements - -ourpythondir = $(pythondir)/grc/gui +ourpythondir = $(grc_src_prefix)/gui ourpython_PYTHON = \ - __init__.py \ + ActionHandler.py \ + Actions.py \ Bars.py \ BlockTreeWindow.py \ + Constants.py \ Dialogs.py \ DrawingArea.py \ FileDialogs.py \ MainWindow.py \ + Messages.py \ NotebookPage.py \ - ParamsDialog.py + ParamsDialog.py \ + Preferences.py \ + StateCache.py \ + __init__.py diff --git a/grc/src/grc/Messages.py b/grc/src/gui/Messages.py index c3db894dc..1d9a80211 100644 --- a/grc/src/grc/Messages.py +++ b/grc/src/gui/Messages.py @@ -16,25 +16,23 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package Messages -#Handle all of the system messages and error reports. -from Constants import VERSION +from .. platforms.base.Constants import VERSION import traceback import sys -## A list of functions that can receive a message. +## A list of functions that can receive a message. MESSENGERS_LIST = list() def register_messenger(messenger): - """! + """ Append the given messenger to the list of messengers. @param messenger a method thats takes a string """ MESSENGERS_LIST.append(messenger) def send(message): - """! + """ Give the message to each of the messengers. @param message a message string """ @@ -44,7 +42,7 @@ def send(message): register_messenger(sys.stdout.write) ########################################################################### -# Special functions for specific program functionalities +# Special functions for specific program functionalities ########################################################################### def send_init(): send("""<<< Welcome to GRC %s >>>\n"""%VERSION) @@ -52,7 +50,7 @@ def send_init(): def send_page_switch(file_path): send('\nShowing: "%s"\n'%file_path) -################# functions for loading flow graphs ######################################## +################# functions for loading flow graphs ######################################## def send_start_load(file_path): send('\nLoading: "%s"'%file_path + '\n') @@ -68,7 +66,7 @@ def send_fail_load(error): send(">>> Failue\n") traceback.print_exc() -################# functions for generating flow graphs ######################################## +################# functions for generating flow graphs ######################################## def send_start_gen(file_path): send('\nGenerating: "%s"'%file_path + '\n') @@ -77,7 +75,7 @@ def send_fail_gen(error): send(">>> Failue\n") traceback.print_exc() -################# functions for executing flow graphs ######################################## +################# functions for executing flow graphs ######################################## def send_start_exec(file_path): send('\nExecuting: "%s"'%file_path + '\n') @@ -87,18 +85,17 @@ def send_verbose_exec(verbose): def send_end_exec(): send("\n>>> Done\n") -################# functions for saving flow graphs ######################################## +################# functions for saving flow graphs ######################################## def send_fail_save(file_path): send('>>> Error: Cannot save: %s\n'%file_path) -################# functions for connections ######################################## +################# functions for connections ######################################## def send_fail_connection(): send('>>> Warning: A connection can only be created between a source and an unconnected sink.\n') -################# functions for preferences ######################################## +################# functions for preferences ######################################## def send_fail_load_preferences(prefs_file_path): send('>>> Error: Cannot load preferences file: "%s"\n'%prefs_file_path) def send_fail_save_preferences(prefs_file_path): send('>>> Error: Cannot save preferences file: "%s"\n'%prefs_file_path) - diff --git a/grc/src/grc/gui/NotebookPage.py b/grc/src/gui/NotebookPage.py index add31b6d6..a25243b18 100644 --- a/grc/src/grc/gui/NotebookPage.py +++ b/grc/src/gui/NotebookPage.py @@ -16,23 +16,21 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.NotebookPage -#A page in the notebook, represents an individual flow graph. -from grc.Actions import * +from Actions import FLOW_GRAPH_CLOSE import pygtk pygtk.require('2.0') import gtk -from grc import ParseXML -from grc.StateCache import StateCache -from grc.Constants import FLOW_GRAPH_DTD +from .. utils import ParseXML +from StateCache import StateCache +from .. platforms.base.Constants import FLOW_GRAPH_DTD import os ############################################################ -## Notebook Page +## Notebook Page ############################################################ -class Page(gtk.HBox): +class NotebookPage(gtk.HBox): """A page in the notebook.""" def __init__(self, main_window, flow_graph, file_path=''): @@ -48,7 +46,7 @@ class Page(gtk.HBox): self.set_file_path(file_path) file_path = file_path or flow_graph.get_parent().get_default_flow_graph() ############################################################ - from grc import converter + from .. utils import converter converter.convert(file_path, flow_graph.get_parent()) ############################################################ ParseXML.validate_dtd(file_path, FLOW_GRAPH_DTD) @@ -84,7 +82,7 @@ class Page(gtk.HBox): self.tab.show_all() def get_generator(self): - """! + """ Get the generator object for this flow graph. @return generator """ @@ -117,35 +115,35 @@ class Page(gtk.HBox): return self.tab def get_pid(self): - """! + """ Get the pid for the flow graph. @return the pid number """ return self.pid def set_pid(self, pid): - """! + """ Set the pid number. @param pid the new pid number """ self.pid = pid def get_flow_graph(self): - """! + """ Get the flow graph. @return the flow graph """ return self._flow_graph def get_file_path(self): - """! + """ Get the file path for the flow graph. @return the file path or '' """ return self.file_path def set_file_path(self, file_path=''): - """! + """ Set the file path, '' for no file path. @param file_path file path string """ @@ -153,23 +151,22 @@ class Page(gtk.HBox): else: self.file_path = '' def get_saved(self): - """! + """ Get the saved status for the flow graph. @return true if saved """ return self.saved def set_saved(self, saved=True): - """! + """ Set the saved status. @param saved boolean status """ self.saved = saved def get_state_cache(self): - """! + """ Get the state cache for the flow graph. @return the state cache """ return self.state_cache - diff --git a/grc/src/grc/gui/ParamsDialog.py b/grc/src/gui/ParamsDialog.py index 771792122..46940db2e 100644 --- a/grc/src/grc/gui/ParamsDialog.py +++ b/grc/src/gui/ParamsDialog.py @@ -16,18 +16,16 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.ParamsDialog -#A dialog for editing a block's parameters. import pygtk pygtk.require('2.0') import gtk from Dialogs import TextDisplay -from grc.Constants import MIN_DIALOG_WIDTH,MIN_DIALOG_HEIGHT +from Constants import MIN_DIALOG_WIDTH, MIN_DIALOG_HEIGHT def get_title_label(title): - """! + """ Get a title label for the params window. The title will be bold, underlined, and left justified. @param title the text of the title @@ -43,7 +41,7 @@ class ParamsDialog(gtk.Dialog): """A dialog box to set block parameters.""" def __init__(self, block): - """! + """ SignalBlockParamsDialog contructor. @param block the signal block """ @@ -92,7 +90,7 @@ class ParamsDialog(gtk.Dialog): self._error_messages_text_display.set_text(messages) def _handle_key_press(self, widget, event): - """! + """ Handle key presses from the keyboard. Call the ok response when enter is pressed. @return false to forward the keypress @@ -102,7 +100,7 @@ class ParamsDialog(gtk.Dialog): return False #forward the keypress def _handle_changed(self, param): - """! + """ A change occured, update any dependent parameters: The enum inside the variable type may have changed and, the variable param will need an external update. @@ -118,7 +116,7 @@ class ParamsDialog(gtk.Dialog): return True def run(self): - """! + """ Call run(). @return true if a change occured. """ @@ -131,4 +129,3 @@ class ParamsDialog(gtk.Dialog): for param in self.block.get_params(): new_data.append(param.get_value()) return original_data != new_data - diff --git a/grc/src/grc/Preferences.py b/grc/src/gui/Preferences.py index e2161d645..a5591500d 100644 --- a/grc/src/grc/Preferences.py +++ b/grc/src/gui/Preferences.py @@ -16,11 +16,9 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.Preferences -#Holds global paramerences -from Constants import HOME_DIR, FLOW_GRAPH_DTD -import ParseXML +from .. platforms.base.Constants import HOME_DIR, FLOW_GRAPH_DTD +from .. utils import ParseXML import Messages import os @@ -93,7 +91,7 @@ Restore previously opened files on start-up. ] ########################################################################### -# Special methods for specific program functionalities +# Special methods for specific program functionalities ########################################################################### def window_size(size=None): @@ -130,4 +128,3 @@ def show_params(): def show_id(): return _get_prefs().show_id_param.get_value() == 'show' - diff --git a/grc/src/grc/StateCache.py b/grc/src/gui/StateCache.py index b973e2742..04b18b18a 100644 --- a/grc/src/grc/StateCache.py +++ b/grc/src/gui/StateCache.py @@ -16,11 +16,8 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package StateCache -#Stores the flow graph states to drive the undo/redo and save interface. from Actions import FLOW_GRAPH_UNDO, FLOW_GRAPH_REDO, get_action_from_name - from Constants import STATE_CACHE_SIZE class StateCache(object): @@ -28,10 +25,10 @@ class StateCache(object): The state cache is an interface to a list to record data/states and to revert to previous states. States are recorded into the list in a circular fassion by using an index for the current state, and counters for the range where states are stored. - """ - + """ + def __init__(self, initial_state): - """! + """ StateCache constructor. @param initial_state the intial state (nested data) """ @@ -41,30 +38,30 @@ class StateCache(object): self.num_next_states = 0 self.states[0] = initial_state self.update_actions() - + def save_new_state(self, state): - """! + """ Save a new state. Place the new state at the next index and add one to the number of previous states. @param state the new state """ self.current_state_index = (self.current_state_index + 1)%STATE_CACHE_SIZE - self.states[self.current_state_index] = state + self.states[self.current_state_index] = state self.num_prev_states = self.num_prev_states + 1 if self.num_prev_states == STATE_CACHE_SIZE: self.num_prev_states = STATE_CACHE_SIZE - 1 self.num_next_states = 0 self.update_actions() - + def get_current_state(self): - """! + """ Get the state at the current index. @return the current state (nested data) """ self.update_actions() - return self.states[self.current_state_index] - + return self.states[self.current_state_index] + def get_prev_state(self): - """! + """ Get the previous state and decrement the current index. @return the previous state or None """ @@ -73,10 +70,10 @@ class StateCache(object): self.num_next_states = self.num_next_states + 1 self.num_prev_states = self.num_prev_states - 1 return self.get_current_state() - return None - + return None + def get_next_state(self): - """! + """ Get the nest state and increment the current index. @return the next state or None """ @@ -86,12 +83,10 @@ class StateCache(object): self.num_prev_states = self.num_prev_states + 1 return self.get_current_state() return None - + def update_actions(self): """ Update the undo and redo actions based on the number of next and prev states. """ get_action_from_name(FLOW_GRAPH_REDO).set_sensitive(self.num_next_states != 0) get_action_from_name(FLOW_GRAPH_UNDO).set_sensitive(self.num_prev_states != 0) - - diff --git a/grc/src/gui/__init__.py b/grc/src/gui/__init__.py new file mode 100644 index 000000000..8b1378917 --- /dev/null +++ b/grc/src/gui/__init__.py @@ -0,0 +1 @@ + diff --git a/grc/src/platforms/Makefile.am b/grc/src/platforms/Makefile.am new file mode 100644 index 000000000..1d3c385c2 --- /dev/null +++ b/grc/src/platforms/Makefile.am @@ -0,0 +1,31 @@ +# +# Copyright 2008 Free Software Foundation, Inc. +# +# This file is part of GNU Radio +# +# GNU Radio is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3, or (at your option) +# any later version. +# +# GNU Radio is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with GNU Radio; see the file COPYING. If not, write to +# the Free Software Foundation, Inc., 51 Franklin Street, +# Boston, MA 02110-1301, USA. +# + +include $(top_srcdir)/grc/Makefile.inc + +SUBDIRS = \ + base \ + gui \ + python + +ourpythondir = $(grc_src_prefix)/platforms + +ourpython_PYTHON = __init__.py diff --git a/grc/src/platforms/__init__.py b/grc/src/platforms/__init__.py new file mode 100644 index 000000000..8b1378917 --- /dev/null +++ b/grc/src/platforms/__init__.py @@ -0,0 +1 @@ + diff --git a/grc/src/grc/elements/Block.py b/grc/src/platforms/base/Block.py index ff43933ec..e3ef84d94 100644 --- a/grc/src/grc/elements/Block.py +++ b/grc/src/platforms/base/Block.py @@ -16,14 +16,12 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.elements.Block -#Flow graph block. -from grc import Utils -from grc.Utils import odict -from grc.elements.Element import Element -from grc.elements.Param import Param -from grc.elements.Port import Port +from ... import utils +from ... utils import odict +from Element import Element +from Param import Param +from Port import Port from Cheetah.Template import Template from UserDict import UserDict @@ -61,10 +59,10 @@ class Block(Element): #grab the data name = n['name'] key = n['key'] - category = Utils.exists_or_else(n, 'category', '') - params = Utils.listify(n, 'param') - sources = Utils.listify(n, 'source') - sinks = Utils.listify(n, 'sink') + category = utils.exists_or_else(n, 'category', '') + params = utils.listify(n, 'param') + sources = utils.listify(n, 'source') + sinks = utils.listify(n, 'sink') #build the block Element.__init__(self, flow_graph) #store the data @@ -121,13 +119,13 @@ class Block(Element): self.test() def test(self): - """! + """ Call test on all children. """ map(lambda c: c.test(), self.get_params() + self.get_sinks() + self.get_sources()) def get_enabled(self): - """! + """ Get the enabled state of the block. @return true for enabled """ @@ -135,7 +133,7 @@ class Block(Element): except: return True def set_enabled(self, enabled): - """! + """ Set the enabled state of the block. @param enabled true for enabled """ @@ -227,7 +225,7 @@ class Block(Element): Any param keys that do not exist will be ignored. @param n the nested data odict """ - params_n = Utils.listify(n, 'param') + params_n = utils.listify(n, 'param') for param_n in params_n: #key and value must exist in the n data if 'key' in param_n.keys() and 'value' in param_n.keys(): diff --git a/grc/src/grc/elements/Connection.py b/grc/src/platforms/base/Connection.py index 36ed14221..3c0b42d78 100644 --- a/grc/src/grc/elements/Connection.py +++ b/grc/src/platforms/base/Connection.py @@ -16,19 +16,14 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.elements.Connection -#Flow graph connection. -#A connection exists between 2 ports. -#One port must be input, one output. -#The port decided whether it can have the connection. -from grc.elements.Element import Element -from grc.Utils import odict +from Element import Element +from ... utils import odict class Connection(Element): def __init__(self, flow_graph, porta, portb): - """! + """ Make a new connection given the parent and 2 ports. @param flow_graph the parent of this element @param porta a port (any direction) @@ -64,7 +59,7 @@ class Connection(Element): except AssertionError: self._add_error_message('Source type "%s" does not match sink type "%s".'%(source_type, sink_type)) def get_enabled(self): - """! + """ Get the enabled state of this connection. @return true if source and sink blocks are enabled """ diff --git a/grc/src/grc/__init__.py b/grc/src/platforms/base/Constants.py.in index d9ba25591..26ba72d97 100644 --- a/grc/src/grc/__init__.py +++ b/grc/src/platforms/base/Constants.py.in @@ -16,6 +16,29 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc -#grc package. +import os + +##The current version of this code +VERSION = '@VERSION@' + +##Location of external data files. +DATA_DIR = '@datadir@' + +##DTD validator for saved flow graphs. +FLOW_GRAPH_DTD = os.path.join(DATA_DIR, 'flow_graph.dtd') + +##The default file extension for flow graphs. +FLOW_GRAPH_FILE_EXTENSION = '.grc' + +##The default file extension for saving flow graph snap shots. +IMAGE_FILE_EXTENSION = '.png' + +##The default path for the open/save dialogs. +DEFAULT_FILE_PATH = os.getcwd() + +##The default icon for the gtk windows. +PY_GTK_ICON = os.path.join(DATA_DIR, 'grc-icon-256.png') + +##The users home directory. +HOME_DIR = os.path.expanduser('~') diff --git a/grc/src/grc/elements/Element.py b/grc/src/platforms/base/Element.py index 936c9d5f6..b6602a314 100644 --- a/grc/src/grc/elements/Element.py +++ b/grc/src/platforms/base/Element.py @@ -16,8 +16,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.elements.Element -#The base class for all elements. class Element(object): @@ -93,4 +91,3 @@ class Element(object): def is_sink(self): return False def is_port(self): return False def is_param(self): return False - diff --git a/grc/src/grc/elements/FlowGraph.py b/grc/src/platforms/base/FlowGraph.py index 94c786d03..bb20c61d0 100644 --- a/grc/src/grc/elements/FlowGraph.py +++ b/grc/src/platforms/base/FlowGraph.py @@ -16,21 +16,18 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.elements.FlowGraph -#Primative flow graph. -from grc import Utils -from grc.Utils import odict -from grc.elements.Element import Element -from grc.elements.Block import Block -from grc.elements.Connection import Connection - -from grc import Messages +from ... import utils +from ... utils import odict +from Element import Element +from Block import Block +from Connection import Connection +from ... gui import Messages class FlowGraph(Element): def __init__(self, platform): - """! + """ Make a flow graph from the arguments. @param platform a platforms with blocks and contrcutors @return the flow graph object @@ -45,7 +42,7 @@ class FlowGraph(Element): def __str__(self): return 'FlowGraph - "%s"'%self.get_option('name') def get_option(self, key): - """! + """ Get the option for a given key. The option comes from the special options block. @param key the param key for the options block @@ -62,7 +59,7 @@ class FlowGraph(Element): def get_blocks(self): return filter(lambda e: e.is_block(), self.get_elements()) def get_connections(self): return filter(lambda e: e.is_connection(), self.get_elements()) def get_elements(self): - """! + """ Get a list of all the elements. Always ensure that the options block is in the list. @return the element list @@ -79,21 +76,21 @@ class FlowGraph(Element): return self._elements def get_enabled_blocks(self): - """! + """ Get a list of all blocks that are enabled. @return a list of blocks """ return filter(lambda b: b.get_enabled(), self.get_blocks()) def get_enabled_connections(self): - """! + """ Get a list of all connections that are enabled. @return a list of connections """ return filter(lambda c: c.get_enabled(), self.get_connections()) def get_new_block(self, key): - """! + """ Get a new block of the specified key. Add the block to the list of elements. @param key the block key @@ -106,7 +103,7 @@ class FlowGraph(Element): return block def connect(self, porta, portb): - """! + """ Create a connection between porta and portb. @param porta a port @param portb another port @@ -119,7 +116,7 @@ class FlowGraph(Element): return connection def remove_element(self, element): - """! + """ Remove the element from the list of elements. If the element is a port, remove the whole block. If the element is a block, remove its connections. @@ -139,7 +136,7 @@ class FlowGraph(Element): self.get_elements().remove(element) def evaluate(self, expr): - """! + """ Evaluate the expression. @param expr the string expression @throw NotImplementedError @@ -185,8 +182,8 @@ class FlowGraph(Element): else: Messages.send_error_load('Flow graph data not found, loading blank flow graph.') fg_n = {} - blocks_n = Utils.listify(fg_n, 'block') - connections_n = Utils.listify(fg_n, 'connection') + blocks_n = utils.listify(fg_n, 'block') + connections_n = utils.listify(fg_n, 'connection') #create option block self._options_block = self.get_parent().get_new_block(self, 'options') self._options_block.get_param('id').set_value('options') @@ -232,4 +229,3 @@ class FlowGraph(Element): self.connect(source, sink) except AssertionError: Messages.send_error_load('Connection between %s(%s) and %s(%s) could not be made.'%(source_block_id, source_key, sink_block_id, sink_key)) self.validate() - diff --git a/grc/src/grc/Makefile.am b/grc/src/platforms/base/Makefile.am index 06edf26cd..dca53b8b5 100644 --- a/grc/src/grc/Makefile.am +++ b/grc/src/platforms/base/Makefile.am @@ -21,28 +21,25 @@ include $(top_srcdir)/grc/Makefile.inc -SUBDIRS = elements gui - -ourpythondir = $(pythondir)/grc +ourpythondir = $(grc_src_prefix)/platforms/base ourpython_PYTHON = \ - __init__.py \ + Block.py \ + Connection.py \ Constants.py \ - converter.py \ - ActionHandler.py \ - Actions.py \ - Messages.py \ - ParseXML.py \ - Preferences.py \ - StateCache.py \ - Utils.py + Element.py \ + FlowGraph.py \ + Param.py \ + Platform.py \ + Port.py \ + __init__.py BUILT_SOURCES = Constants.py Constants.py: Makefile $(srcdir)/Constants.py.in sed \ - -e 's|@VERSION[@]|@VERSION@|g' \ - -e 's|@datadir[@]|$(grc_data_dir)|g' \ + -e 's|@VERSION[@]|$(VERSION)|g' \ + -e 's|@datadir[@]|$(grc_base_data_dir)|g' \ $(srcdir)/Constants.py.in > $@ EXTRA_DIST = Constants.py.in diff --git a/grc/src/grc/elements/Param.py b/grc/src/platforms/base/Param.py index a8aa43004..3a8d98c30 100644 --- a/grc/src/grc/elements/Param.py +++ b/grc/src/platforms/base/Param.py @@ -16,13 +16,10 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.elements.Param -#Flow graph block parameters. -#And options for enum type paramater. -from grc import Utils -from grc.Utils import odict -from grc.elements.Element import Element +from ... import utils +from ... utils import odict +from Element import Element class Option(Element): @@ -67,7 +64,7 @@ class Option(Element): #grab the data name = n['name'] key = n['key'] - opts = Utils.listify(n, 'opt') + opts = utils.listify(n, 'opt') #build the option return Option( param=param, @@ -92,10 +89,10 @@ class Param(Element): #grab the data name = n['name'] key = n['key'] - value = Utils.exists_or_else(n, 'value', '') + value = utils.exists_or_else(n, 'value', '') type = n['type'] - hide = Utils.exists_or_else(n, 'hide', '') - options = Utils.listify(n, 'option') + hide = utils.exists_or_else(n, 'hide', '') + options = utils.listify(n, 'option') #build the param Element.__init__(self, block) self._name = name @@ -153,14 +150,14 @@ class Param(Element): except AssertionError: self._add_error_message('Type "%s" is not a possible type.'%self.get_type()) def evaluate(self): - """! + """ Evaluate the value of this param. @throw NotImplementedError """ raise NotImplementedError def to_code(self): - """! + """ Convert the value to code. @throw NotImplementedError """ diff --git a/grc/src/grc/elements/Platform.py b/grc/src/platforms/base/Platform.py index bf09bef0c..c25b4a050 100644 --- a/grc/src/grc/elements/Platform.py +++ b/grc/src/platforms/base/Platform.py @@ -16,24 +16,22 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.elements.Platform -#A Platform contains all blocks in platform. import os -from grc import ParseXML -from grc import Utils -from grc.elements.Element import Element as _Element -from grc.elements.FlowGraph import FlowGraph as _FlowGraph -from grc.elements.Connection import Connection as _Connection -from grc.elements.Block import Block as _Block -from grc.elements.Port import Port as _Port -from grc.elements.Param import Param as _Param -from grc.Constants import DATA_DIR +from ... utils import ParseXML +from ... import utils +from Element import Element as _Element +from FlowGraph import FlowGraph as _FlowGraph +from Connection import Connection as _Connection +from Block import Block as _Block +from Port import Port as _Port +from Param import Param as _Param +from Constants import DATA_DIR class Platform(_Element): def __init__(self, name, key, block_paths, block_dtd, block_tree, default_flow_graph, generator): - """! + """ Make a platform from the arguments. @param name the platform name @param key the unique platform key @@ -60,14 +58,14 @@ class Platform(_Element): for block_path in self._block_paths: if os.path.isfile(block_path): self._load_block(block_path) elif os.path.isdir(block_path): - for dirpath,dirnames,filenames in os.walk(block_path): + for dirpath, dirnames, filenames in os.walk(block_path): for filename in filter(lambda f: f.endswith('.xml'), filenames): self._load_block(os.path.join(dirpath, filename)) def get_prefs_block(self): return self.get_new_flow_graph().get_new_block('preferences') def _load_block(self, f): - """! + """ Load the block wrapper from the file path. The block wrapper must pass validation, and have a unique block key. If any of the checks fail, exit with error. @@ -86,7 +84,7 @@ class Platform(_Element): self._blocks_n[key] = n def load_block_tree(self, block_tree): - """! + """ Load a block tree with categories and blocks. Step 1: Load all blocks from the xml specification. Step 2: Load blocks with builtin category specifications. @@ -98,9 +96,9 @@ class Platform(_Element): parent = '%s/%s'%(parent, cat_n['name']) block_tree.add_block(parent) #recursive call to load sub categories - map(lambda c: load_category(c, parent), Utils.listify(cat_n, 'cat')) + map(lambda c: load_category(c, parent), utils.listify(cat_n, 'cat')) #add blocks in this category - for block_key in Utils.listify(cat_n, 'block'): + for block_key in utils.listify(cat_n, 'block'): block_tree.add_block(parent, self.get_block(block_key)) #load the block tree f = self._block_tree diff --git a/grc/src/grc/elements/Port.py b/grc/src/platforms/base/Port.py index 9da521156..61134791c 100644 --- a/grc/src/grc/elements/Port.py +++ b/grc/src/platforms/base/Port.py @@ -16,11 +16,9 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.elements.Port -#Flow graph block port (source or sink). -from grc import Utils -from grc.elements.Element import Element +from ... import utils +from Element import Element class Port(Element): @@ -45,7 +43,7 @@ class Port(Element): self._type = type def validate(self): - """! + """ Validate the port. The port must be non-empty and type must a possible type. """ @@ -75,7 +73,7 @@ class Port(Element): def get_type(self): return self.get_parent().resolve_dependencies(self._type) def get_connections(self): - """! + """ Get all connections that use this port. @return a list of connection objects """ @@ -84,14 +82,14 @@ class Port(Element): return connections def is_connected(self): - """! + """ Is this port connected? @return true if at least one connection """ return bool(self.get_connections()) def is_full(self): - """! + """ Is this port full of connections? Generally a sink can handle one connection and a source can handle many. @return true if the port is full @@ -100,7 +98,7 @@ class Port(Element): if self.is_sink(): return bool(self.get_connections()) def is_empty(self): - """! + """ Is this port empty? An empty port has no connections. @return true if empty diff --git a/grc/src/platforms/base/__init__.py b/grc/src/platforms/base/__init__.py new file mode 100644 index 000000000..8b1378917 --- /dev/null +++ b/grc/src/platforms/base/__init__.py @@ -0,0 +1 @@ + diff --git a/grc/src/grc/gui/elements/Block.py b/grc/src/platforms/gui/Block.py index ee19ee2f6..d38e17133 100644 --- a/grc/src/grc/gui/elements/Block.py +++ b/grc/src/platforms/gui/Block.py @@ -16,14 +16,17 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.elements.Block -#The graphical signal block. -from grc import Preferences +from ... gui import Preferences from Element import Element import Utils import Colors -from grc.Constants import * +from ... gui.Constants import BORDER_PROXIMITY_SENSITIVITY +from Constants import \ + BLOCK_FONT, LABEL_PADDING_WIDTH, \ + LABEL_PADDING_HEIGHT, PORT_HEIGHT, \ + PORT_SEPARATION, LABEL_SEPARATION, \ + PORT_BORDER_SEPARATION, POSSIBLE_ROTATIONS import pygtk pygtk.require('2.0') import gtk @@ -33,7 +36,7 @@ class Block(Element): """The graphical signal block.""" def __init__(self, *args, **kwargs): - """! + """ Block contructor. Add graphics related params to the block. """ @@ -61,7 +64,7 @@ class Block(Element): Element.__init__(self) def get_coordinate(self): - """! + """ Get the coordinate from the position param. @return the coordinate tuple (x, y) or (0, 0) if failure """ @@ -83,14 +86,14 @@ class Block(Element): return (0, 0) def set_coordinate(self, coor): - """! + """ Set the coordinate into the position param. @param coor the coordinate tuple (x, y) """ self.get_param('_coordinate').set_value(str(coor)) def get_rotation(self): - """! + """ Get the rotation from the position param. @return the rotation in degrees or 0 if failure """ @@ -102,7 +105,7 @@ class Block(Element): return POSSIBLE_ROTATIONS[0] def set_rotation(self, rot): - """! + """ Set the rotation into the position param. @param rot the rotation in degrees """ @@ -164,7 +167,7 @@ class Block(Element): for j in range(height): vimage.put_pixel(j, width-i-1, image.get_pixel(i, j)) def draw(self, window): - """! + """ Draw the signal block with label and inputs/outputs. @param window the gtk window to draw on """ @@ -181,7 +184,7 @@ class Block(Element): map(lambda p: p.draw(window), self.get_ports()) def what_is_selected(self, coor, coor_m=None): - """! + """ Get the element that is selected. @param coor the (x,y) tuple @param coor_m the (x_m, y_m) tuple @@ -191,4 +194,3 @@ class Block(Element): port_selected = port.what_is_selected(coor, coor_m) if port_selected: return port_selected return Element.what_is_selected(self, coor, coor_m) - diff --git a/grc/src/grc/gui/elements/Colors.py b/grc/src/platforms/gui/Colors.py index 1eedde0a0..353cd1c9f 100644 --- a/grc/src/grc/gui/elements/Colors.py +++ b/grc/src/platforms/gui/Colors.py @@ -16,8 +16,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.elements.Colors -#Global Colors for the gui import pygtk pygtk.require('2.0') diff --git a/grc/src/grc/gui/elements/Connection.py b/grc/src/platforms/gui/Connection.py index 2d99518a8..44048e181 100644 --- a/grc/src/grc/gui/elements/Connection.py +++ b/grc/src/platforms/gui/Connection.py @@ -16,19 +16,17 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.elements.Connection -#The graphical connection for input/output ports. import Utils from Element import Element import Colors -from grc.Constants import CONNECTOR_ARROW_BASE,CONNECTOR_ARROW_HEIGHT +from Constants import CONNECTOR_ARROW_BASE, CONNECTOR_ARROW_HEIGHT class Connection(Element): """A graphical connection for ports.""" def get_coordinate(self): - """! + """ Get the 0,0 coordinate. Coordinates are irrelevant in connection. @return 0, 0 @@ -36,7 +34,7 @@ class Connection(Element): return (0, 0) def get_rotation(self): - """! + """ Get the 0 degree rotation. Rotations are irrelevant in connection. @return 0 @@ -107,7 +105,7 @@ class Connection(Element): self.add_line((x2, y2), points[0]) def draw(self, window): - """! + """ Draw the connection. @param window the gtk window to draw on """ diff --git a/grc/src/platforms/gui/Constants.py b/grc/src/platforms/gui/Constants.py new file mode 100644 index 000000000..b2e9bfed5 --- /dev/null +++ b/grc/src/platforms/gui/Constants.py @@ -0,0 +1,44 @@ +# +# Copyright 2008 Free Software Foundation, Inc. +# +# This file is part of GNU Radio +# +# GNU Radio is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3, or (at your option) +# any later version. +# +# GNU Radio is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with GNU Radio; see the file COPYING. If not, write to +# the Free Software Foundation, Inc., 51 Franklin Street, +# Boston, MA 02110-1301, USA. +# + +#label constraint dimensions +LABEL_SEPARATION = 3 +LABEL_PADDING_WIDTH = 9 +LABEL_PADDING_HEIGHT = 9 +#port constraint dimensions +PORT_SEPARATION = 17 +PORT_HEIGHT = 15 +PORT_WIDTH = 25 +PORT_BORDER_SEPARATION = 9 +#fonts +PARAM_LABEL_FONT = 'Sans 9.5' +PARAM_FONT = 'Sans 7.5' +BLOCK_FONT = 'Sans 8' +PORT_FONT = 'Sans 7.5' +#minimal length of connector +CONNECTOR_EXTENSION_MINIMAL = 11 +#increment length for connector +CONNECTOR_EXTENSION_INCREMENT = 11 +#connection arrow dimensions +CONNECTOR_ARROW_BASE = 13 +CONNECTOR_ARROW_HEIGHT = 17 +#possible rotations in degrees +POSSIBLE_ROTATIONS = (0, 90, 180, 270) diff --git a/grc/src/grc/gui/elements/Element.py b/grc/src/platforms/gui/Element.py index 1d7157eb5..f97d85ff6 100644 --- a/grc/src/grc/gui/elements/Element.py +++ b/grc/src/platforms/gui/Element.py @@ -16,16 +16,14 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.elements.Element -#Base class for graphical elements such as: -#signal blocks, input sockets, output sockets and connections. import Colors import pygtk pygtk.require('2.0') import gtk import pango -from grc.Constants import * +from ... gui.Constants import CONNECTION_SELECT_SENSITIVITY +from Constants import POSSIBLE_ROTATIONS class Element(object): """ @@ -35,7 +33,7 @@ class Element(object): """ def __init__(self, *args, **kwargs): - """! + """ Make a new list of rectangular areas and lines, and set the coordinate and the rotation. """ self.set_rotation(POSSIBLE_ROTATIONS[0]) @@ -44,7 +42,7 @@ class Element(object): self.set_highlighted(False) def is_horizontal(self, rotation=None): - """! + """ Is this element horizontal? If rotation is None, use this element's rotation. @param rotation the optional rotation @@ -54,7 +52,7 @@ class Element(object): return rotation in (0, 180) def is_vertical(self, rotation=None): - """! + """ Is this element vertical? If rotation is None, use this element's rotation. @param rotation the optional rotation @@ -66,7 +64,7 @@ class Element(object): def get_gc(self): return self._gc def draw(self, window, BG_color=Colors.BG_COLOR, FG_color=Colors.FG_COLOR): - """! + """ Draw in the given window. @param window the gtk window to draw on @param BG_color the background color @@ -87,7 +85,7 @@ class Element(object): window.draw_line(gc, X+x1, Y+y1, X+x2, Y+y2) def rotate(self, direction): - """! + """ Rotate all of the areas by 90 degrees. @param direction 90 or 270 degrees """ @@ -99,41 +97,41 @@ class Element(object): self.lines_dict = dict((rotation, list()) for rotation in POSSIBLE_ROTATIONS) def set_coordinate(self, coor): - """! + """ Set the reference coordinate. @param coor the coordinate tuple (x,y) """ self.coor = coor def get_parent(self): - """! + """ Get the parent of this element. @return the parent """ return self.parent def set_highlighted(self, highlighted): - """! + """ Set the highlight status. @param highlighted true to enable highlighting """ self.highlighted = highlighted def is_highlighted(self): - """! + """ Get the highlight status. @return true if highlighted """ return self.highlighted def get_coordinate(self): - """!Get the coordinate. + """Get the coordinate. @return the coordinate tuple (x,y) """ return self.coor def move(self, delta_coor): - """! + """ Move the element by adding the delta_coor to the current coordinate. @param delta_coor (delta_x,delta_y) tuple """ @@ -142,7 +140,7 @@ class Element(object): self.set_coordinate((X+deltaX, Y+deltaY)) def add_area(self, rel_coor, area, rotation=None): - """! + """ Add an area to the area list. An area is actually a coordinate relative to the main coordinate with a width/height pair relative to the area coordinate. @@ -157,7 +155,7 @@ class Element(object): self.areas_dict[rotation or self.get_rotation()].append((rel_coor, area)) def add_line(self, rel_coor1, rel_coor2, rotation=None): - """! + """ Add a line to the line list. A line is defined by 2 relative coordinates. Lines must be horizontal or vertical. @@ -170,7 +168,7 @@ class Element(object): self.lines_dict[rotation or self.get_rotation()].append((rel_coor1, rel_coor2)) def what_is_selected(self, coor, coor_m=None): - """! + """ One coordinate specified: Is this element selected at given coordinate? ie: is the coordinate encompassed by one of the areas or lines? @@ -212,22 +210,20 @@ class Element(object): return None def get_rotation(self): - """! + """ Get the rotation in degrees. @return the rotation """ return self.rotation def set_rotation(self, rotation): - """! + """ Set the rotation in degrees. @param rotation the rotation""" if rotation not in POSSIBLE_ROTATIONS: - raise Exception('"%s" is not one of the possible rotations: (%s)'%(rotation,POSSIBLE_ROTATIONS)) + raise Exception('"%s" is not one of the possible rotations: (%s)'%(rotation, POSSIBLE_ROTATIONS)) self.rotation = rotation def update(self): """Do nothing for the update. Dummy method.""" pass - - diff --git a/grc/src/grc/gui/elements/FlowGraph.py b/grc/src/platforms/gui/FlowGraph.py index b4d835277..1e654e1bf 100644 --- a/grc/src/grc/gui/elements/FlowGraph.py +++ b/grc/src/platforms/gui/FlowGraph.py @@ -16,26 +16,26 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.elements.FlowGraph -#A flow graph structure for storing signal blocks and their connections. -from grc import Preferences -from grc import Utils -from grc.Constants import * -from grc.Actions import * +from ... gui import Preferences +from ... gui.Constants import \ + DIR_LEFT, DIR_RIGHT, \ + SCROLL_PROXIMITY_SENSITIVITY, SCROLL_DISTANCE, \ + MOTION_DETECT_REDRAWING_SENSITIVITY +from ... gui.Actions import \ + ELEMENT_CREATE, ELEMENT_SELECT, \ + BLOCK_PARAM_MODIFY, BLOCK_MOVE import Colors import Utils -from grc.gui.ParamsDialog import ParamsDialog +from ... gui.ParamsDialog import ParamsDialog from Element import Element -from grc.elements import FlowGraph as _FlowGraph - +from .. base import FlowGraph as _FlowGraph import pygtk pygtk.require('2.0') import gtk - import random import time -from grc import Messages +from ... gui import Messages class FlowGraph(Element): """ @@ -45,7 +45,7 @@ class FlowGraph(Element): """ def __init__(self, *args, **kwargs): - """! + """ FlowGraph contructor. Create a list for signal blocks and connections. Connect mouse handlers. """ @@ -63,7 +63,7 @@ class FlowGraph(Element): self._new_selected_port = None def _get_unique_id(self, base_id=''): - """! + """ Get a unique id starting with the base id. @param base_id the id starts with this and appends a count @return a unique id @@ -88,7 +88,7 @@ class FlowGraph(Element): def get_ctrl_mask(self): return self.drawing_area.ctrl_mask def add_new_block(self, key): - """! + """ Add a block of the given key to this flow graph. @param key the block key """ @@ -109,7 +109,7 @@ class FlowGraph(Element): # Copy Paste ########################################################################### def copy_to_clipboard(self): - """! + """ Copy the selected blocks and connections into the clipboard. @return the clipboard """ @@ -135,7 +135,7 @@ class FlowGraph(Element): return clipboard def paste_from_clipboard(self, clipboard): - """! + """ Paste the blocks and connections from the clipboard. @param clipboard the nested data of blocks, connections """ @@ -180,7 +180,7 @@ class FlowGraph(Element): # Modify Selected ########################################################################### def type_controller_modify_selected(self, direction): - """! + """ Change the registered type controller for the selected signal blocks. @param direction +1 or -1 @return true for change @@ -205,7 +205,7 @@ class FlowGraph(Element): return changed def port_controller_modify_selected(self, direction): - """! + """ Change port controller for the selected signal blocks. @param direction +1 or -1 @return true for changed @@ -221,14 +221,14 @@ class FlowGraph(Element): try: value = param.evaluate() value = value + direction - assert(0 < value <= MAX_NUM_PORTS) + assert 0 < value param.set_value(value) changed = True except: pass return changed def param_modify_selected(self): - """! + """ Create and show a param modification dialog for the selected block. @return true if parameters were changed """ @@ -238,7 +238,7 @@ class FlowGraph(Element): return False def enable_selected(self, enable): - """! + """ Enable/disable the selected blocks. @param enable true to enable @return true if changed @@ -251,7 +251,7 @@ class FlowGraph(Element): return changed def move_selected(self, delta_coordinate): - """! + """ Move the element and by the change in coordinates. @param delta_coordinate the change in coordinates """ @@ -260,7 +260,7 @@ class FlowGraph(Element): self.element_moved = True def rotate_selected(self, direction): - """! + """ Rotate the selected blocks by 90 degrees. @param direction DIR_LEFT or DIR_RIGHT @return true if changed, otherwise false. @@ -288,7 +288,7 @@ class FlowGraph(Element): return True def remove_selected(self): - """! + """ Remove selected elements @return true if changed. """ @@ -299,7 +299,7 @@ class FlowGraph(Element): return changed def draw(self): - """! + """ Draw the background and grid if enabled. Draw all of the elements in this flow graph onto the pixmap. Draw the pixmap to the drawable window of this flow graph. @@ -340,14 +340,14 @@ class FlowGraph(Element): self.get_drawing_area().draw() def update(self): - """! + """ Update highlighting so only the selected is highlighted. Call update on all elements. Resize the window if size changed. """ #update highlighting map(lambda e: e.set_highlighted(False), self.get_elements()) - for selected_element in self.get_selected_elements(): + for selected_element in self.get_selected_elements(): selected_element.set_highlighted(True) #update all elements map(lambda e: e.update(), self.get_elements()) @@ -361,13 +361,13 @@ class FlowGraph(Element): ## Get Selected ########################################################################## def unselect(self): - """! + """ Set selected elements to an empty set. """ self._selected_elements = [] def what_is_selected(self, coor, coor_m=None): - """! + """ What is selected? At the given coordinate, return the elements found to be selected. If coor_m is unspecified, return a list of only the first element found to be selected: @@ -385,7 +385,7 @@ class FlowGraph(Element): selected_element = element.what_is_selected(coor, coor_m) if not selected_element: continue #update the selected port information - if selected_element.is_port(): + if selected_element.is_port(): if not coor_m: selected_port = selected_element selected_element = selected_element.get_parent() selected.add(selected_element) @@ -400,7 +400,7 @@ class FlowGraph(Element): return list(selected) def get_selected_connections(self): - """! + """ Get a group of selected connections. @return sub set of connections in this flow graph """ @@ -410,7 +410,7 @@ class FlowGraph(Element): return list(selected) def get_selected_blocks(self): - """! + """ Get a group of selected blocks. @return sub set of blocks in this flow graph """ @@ -420,28 +420,28 @@ class FlowGraph(Element): return list(selected) def get_selected_block(self): - """! + """ Get the selected block when a block or port is selected. @return a block or None """ return self.get_selected_blocks() and self.get_selected_blocks()[0] or None def get_selected_elements(self): - """! + """ Get the group of selected elements. @return sub set of elements in this flow graph """ return self._selected_elements def get_selected_element(self): - """! + """ Get the selected element. @return a block, port, or connection or None """ return self.get_selected_elements() and self.get_selected_elements()[0] or None def update_selected_elements(self): - """! + """ Update the selected elements. The update behavior depends on the state of the mouse button. When the mouse button pressed the selection will change when @@ -488,7 +488,7 @@ class FlowGraph(Element): ## Event Handlers ########################################################################## def handle_mouse_button_press(self, left_click, double_click, coordinate): - """! + """ A mouse button is pressed, only respond to left clicks. Find the selected element. Attempt a new connection if possible. Open the block params window on a double click. @@ -506,7 +506,7 @@ class FlowGraph(Element): self.handle_states(BLOCK_PARAM_MODIFY) def handle_mouse_button_release(self, left_click, coordinate): - """! + """ A mouse button is released, record the state. """ if not left_click: return @@ -530,7 +530,7 @@ class FlowGraph(Element): self.draw() def handle_mouse_motion(self, coordinate): - """! + """ The mouse has moved, respond to mouse dragging. Move a selected element to the new coordinate. Auto-scroll the scroll bars at the boundaries. diff --git a/grc/src/grc/gui/elements/Makefile.am b/grc/src/platforms/gui/Makefile.am index f075d4209..2e3972ef3 100644 --- a/grc/src/grc/gui/elements/Makefile.am +++ b/grc/src/platforms/gui/Makefile.am @@ -19,18 +19,19 @@ # Boston, MA 02110-1301, USA. # -include $(top_srcdir)/Makefile.common +include $(top_srcdir)/grc/Makefile.inc -ourpythondir = $(pythondir)/grc/gui/elements +ourpythondir = $(grc_src_prefix)/platforms/gui ourpython_PYTHON = \ - __init__.py \ Block.py \ Colors.py \ + Constants.py \ Connection.py \ Element.py \ FlowGraph.py \ Param.py \ Platform.py \ Port.py \ - Utils.py + Utils.py \ + __init__.py diff --git a/grc/src/grc/gui/elements/Param.py b/grc/src/platforms/gui/Param.py index e23407725..f45d80bba 100644 --- a/grc/src/grc/gui/elements/Param.py +++ b/grc/src/platforms/gui/Param.py @@ -16,8 +16,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.elements.Param -#GTK objects for handling input and the signal block parameter class. import Utils from Element import Element @@ -26,7 +24,7 @@ pygtk.require('2.0') import gtk import pango import gobject -from grc.Constants import * +from Constants import PARAM_LABEL_FONT, PARAM_FONT from os import path ###################################################################################################### @@ -118,14 +116,14 @@ class Param(Element): """The graphical parameter.""" def update(self): - """! + """ Called when an external change occurs. Update the graphical input by calling the change handler. """ if hasattr(self, 'input'): self._handle_changed() def get_input_object(self, callback=None): - """! + """ Get the graphical gtk class to represent this parameter. Create the input object with this data type and the handle changed method. @param callback a function of one argument(this param) to be called from the change handler @@ -136,10 +134,11 @@ class Param(Element): elif self.get_type() in ('file_open', 'file_save'): input = FileParam else: input = EntryParam self.input = input(self, self._handle_changed) + if not callback: self.update() return self.input def _handle_changed(self, widget=None): - """! + """ When the input changes, write the inputs to the data type. Finish by calling the exteral callback. """ @@ -167,7 +166,7 @@ class Param(Element): if self.callback: self.callback(self) def get_markup(self): - """! + """ Create a markup to display the Param as a label on the SignalBlock. If the data type is an Enum type, use the cname of the Enum's current choice. Otherwise, use parsed the data type and use its string representation. @@ -211,7 +210,7 @@ class Param(Element): else: return '<span foreground="red"><b>%s:</b> error</span>'%Utils.xml_encode(self.get_name()) def get_layout(self): - """! + """ Create a layout based on the current markup. @return the pango layout """ @@ -220,4 +219,3 @@ class Param(Element): desc = pango.FontDescription(PARAM_FONT) layout.set_font_description(desc) return layout - diff --git a/grc/src/grc/gui/elements/Platform.py b/grc/src/platforms/gui/Platform.py index 779a14303..a32b0209f 100644 --- a/grc/src/grc/gui/elements/Platform.py +++ b/grc/src/platforms/gui/Platform.py @@ -16,8 +16,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.elements.Platform -#Graphical platform to turn an existing platform into a gui platform. from FlowGraph import FlowGraph from Connection import Connection @@ -32,7 +30,7 @@ class %s(c1, c2): c1.__init__(self, *args, **kwargs) c2.__init__(self, *args, **kwargs) """%name, locals()) - return locals()[name] + return locals()[name] def Platform(platform): #combine with gui class @@ -44,8 +42,7 @@ def Platform(platform): ('Sink', Port), ('Param', Param), ): - old_value = getattr(platform, attr) - c = conjoin_classes(attr, old_value, value) + old_value = getattr(platform, attr) + c = conjoin_classes(attr, old_value, value) setattr(platform, attr, c) return platform - diff --git a/grc/src/grc/gui/elements/Port.py b/grc/src/platforms/gui/Port.py index 3449f1b9e..aeab85ea0 100644 --- a/grc/src/grc/gui/elements/Port.py +++ b/grc/src/platforms/gui/Port.py @@ -16,11 +16,12 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.elements.Port -#The graphical input/output sockets of the signal block. from Element import Element -from grc.Constants import * +from Constants import \ + PORT_HEIGHT, PORT_SEPARATION, \ + PORT_WIDTH, CONNECTOR_EXTENSION_MINIMAL, \ + CONNECTOR_EXTENSION_INCREMENT, PORT_FONT import Colors import pygtk pygtk.require('2.0') @@ -31,7 +32,7 @@ class Port(Element): """The graphical port.""" def __init__(self, *args, **kwargs): - """! + """ Port contructor. Create list of connector coordinates. """ @@ -76,7 +77,7 @@ class Port(Element): self.add_area((x, y), (PORT_HEIGHT, PORT_WIDTH)) self._connector_coordinate = (x+PORT_HEIGHT/2, y+1+PORT_WIDTH) #the connector length - self._connector_length = CONNECTOR_EXTENSION_INITIAL_LENGTH + CONNECTOR_EXTENSION_LENGTH*index + self._connector_length = CONNECTOR_EXTENSION_MINIMAL + CONNECTOR_EXTENSION_INCREMENT*index def _create_labels(self): """Create the labels for the socket.""" @@ -100,7 +101,7 @@ class Port(Element): for j in range(h): vimage.put_pixel(j, w-i-1, image.get_pixel(i, j)) def draw(self, window): - """! + """ Draw the socket with a label. @param window the gtk window to draw on """ @@ -115,7 +116,7 @@ class Port(Element): window.draw_image(gc, self.vertical_label, 0, 0, x+X+(PORT_HEIGHT-self.h)/2, y+Y+(PORT_WIDTH-self.w)/2, -1, -1) def get_connector_coordinate(self): - """! + """ Get the coordinate where connections may attach to. @return the connector coordinate (x, y) tuple """ @@ -124,7 +125,7 @@ class Port(Element): return (x+X, y+Y) def get_connector_direction(self): - """! + """ Get the direction that the socket points: 0,90,180,270. This is the rotation degree if the socket is an output or the rotation degree + 180 if the socket is an input. @@ -134,7 +135,7 @@ class Port(Element): elif self.is_sink(): return (self.get_rotation() + 180)%360 def get_connector_length(self): - """! + """ Get the length of the connector. The connector length increases as the port index changes. @return the length in pixels @@ -142,42 +143,42 @@ class Port(Element): return self._connector_length def get_rotation(self): - """! + """ Get the parent's rotation rather than self. @return the parent's rotation """ return self.get_parent().get_rotation() def move(self, delta_coor): - """! + """ Move the parent rather than self. @param delta_corr the (delta_x, delta_y) tuple """ self.get_parent().move(delta_coor) def rotate(self, direction): - """! + """ Rotate the parent rather than self. @param direction degrees to rotate """ self.get_parent().rotate(direction) def get_coordinate(self): - """! + """ Get the parent's coordinate rather than self. @return the parents coordinate """ return self.get_parent().get_coordinate() def set_highlighted(self, highlight): - """! + """ Set the parent highlight rather than self. @param highlight true to enable highlighting """ self.get_parent().set_highlighted(highlight) def is_highlighted(self): - """! + """ Get the parent's is highlight rather than self. @return the parent's highlighting status """ diff --git a/grc/src/grc/gui/elements/Utils.py b/grc/src/platforms/gui/Utils.py index 602a7c546..17750ef45 100644 --- a/grc/src/grc/gui/elements/Utils.py +++ b/grc/src/platforms/gui/Utils.py @@ -16,13 +16,11 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.elements.Utils -#Shared functions for flow graph elements. -from grc.Constants import POSSIBLE_ROTATIONS +from Constants import POSSIBLE_ROTATIONS def get_rotated_coordinate(coor, rotation): - """! + """ Rotate the coordinate by the given rotation. @param coor the coordinate x, y tuple @param rotation the angle in degrees @@ -42,7 +40,7 @@ def get_rotated_coordinate(coor, rotation): return (x*cos_r + y*sin_r, -x*sin_r + y*cos_r) def get_angle_from_coordinates((x1,y1), (x2,y2)): - """! + """ Given two points, calculate the vector direction from point1 to point2, directions are multiples of 90 degrees. @param (x1,y1) the coordinate of point 1 @param (x2,y2) the coordinate of point 2 @@ -71,4 +69,3 @@ def xml_encode(string): ("'", '''), ): string = string.replace(char, safe) return string - diff --git a/grc/src/platforms/gui/__init__.py b/grc/src/platforms/gui/__init__.py new file mode 100644 index 000000000..8b1378917 --- /dev/null +++ b/grc/src/platforms/gui/__init__.py @@ -0,0 +1 @@ + diff --git a/grc/src/grc_gnuradio/Block.py b/grc/src/platforms/python/Block.py index 84909e763..655a6ec55 100644 --- a/grc/src/grc_gnuradio/Block.py +++ b/grc/src/platforms/python/Block.py @@ -16,12 +16,10 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.Block -#Flow graph block. -from grc.elements.Block import Block as _Block -from grc import Utils +from .. base.Block import Block as _Block from utils import extract_docs +from ... import utils class Block(_Block): @@ -38,11 +36,11 @@ class Block(_Block): @return block a new block """ #grab the data - doc = Utils.exists_or_else(n, 'doc', '') - imports = map(lambda i: i.strip(), Utils.listify(n, 'import')) + doc = utils.exists_or_else(n, 'doc', '') + imports = map(lambda i: i.strip(), utils.listify(n, 'import')) make = n['make'] - checks = Utils.listify(n, 'check') - callbacks = Utils.listify(n, 'callback') + checks = utils.listify(n, 'check') + callbacks = utils.listify(n, 'callback') #build the block _Block.__init__( self, @@ -56,7 +54,7 @@ class Block(_Block): self._checks = checks def validate(self): - """! + """ Validate this block. Call the base class validate. Evaluate the checks: each check must evaluate to True. @@ -111,7 +109,7 @@ class Block(_Block): return '\n'.join([doc, extract_docs.extract(self.get_key())]).strip('\n') def get_imports(self): - """! + """ Resolve all import statements. Split each import statement at newlines. Combine all import statments into a list. @@ -123,7 +121,7 @@ class Block(_Block): def get_make(self): return self.resolve_dependencies(self._make) def get_callbacks(self): - """! + """ Get a list of function callbacks for this block. @return a list of strings """ diff --git a/grc/src/grc_gnuradio/Connection.py b/grc/src/platforms/python/Connection.py index fd2f7aa06..f742ff63d 100644 --- a/grc/src/grc_gnuradio/Connection.py +++ b/grc/src/platforms/python/Connection.py @@ -16,16 +16,11 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.Connection -#Flow graph connection. -#A connection exists between 2 ports. -#One port must be input, one output. -#The port decided whether it can have the connection. -from grc.elements.Connection import Connection as _Connection +from .. base.Connection import Connection as _Connection class Connection(_Connection): - + def validate(self): """ Validate the connections. @@ -37,5 +32,3 @@ class Connection(_Connection): sink_vlen = self.get_sink().get_vlen() try: assert(source_vlen == sink_vlen) except AssertionError: self._add_error_message('Source vector length "%s" does not match sink vector length "%s".'%(source_vlen, sink_vlen)) - - diff --git a/grc/src/grc_gnuradio/Constants.py.in b/grc/src/platforms/python/Constants.py.in index 66b773e79..c2d878ba3 100644 --- a/grc/src/grc_gnuradio/Constants.py.in +++ b/grc/src/platforms/python/Constants.py.in @@ -16,9 +16,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.Constants -#Global constants for grc gnuradio package -#@author Josh Blum import os import sys @@ -41,4 +38,3 @@ FLOW_GRAPH_TEMPLATE = os.path.join(DATA_DIR, 'flow_graph.tmpl') BLOCK_DTD = os.path.join(DATA_DIR, 'block.dtd') BLOCK_TREE = os.path.join(DATA_DIR, 'block_tree.xml') DEFAULT_FLOW_GRAPH = os.path.join(DATA_DIR, 'default_flow_graph.grc.xml') - diff --git a/grc/src/grc_gnuradio/FlowGraph.py b/grc/src/platforms/python/FlowGraph.py index e9e876bbe..6c9b7f642 100644 --- a/grc/src/grc_gnuradio/FlowGraph.py +++ b/grc/src/platforms/python/FlowGraph.py @@ -16,16 +16,14 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.FlowGraph -#Primative flow graph. from utils import expr_utils -from grc.elements.FlowGraph import FlowGraph as _FlowGraph +from .. base.FlowGraph import FlowGraph as _FlowGraph from Block import Block from Connection import Connection def get_variable_code(variable): - """! + """ Get the code representation for a variable. Normally this is the value parameter. For the variable chooser, use the index and choices. @@ -43,7 +41,7 @@ def get_variable_code(variable): class FlowGraph(_FlowGraph): def _get_io_signature(self, pad_key): - """! + """ Get an io signature for this flow graph. The pad key determines the directionality of the io signature. @param pad_key a string of pad_source or pad_sink @@ -66,7 +64,7 @@ class FlowGraph(_FlowGraph): } def get_input_signature(self): - """! + """ Get the io signature for the input side of this flow graph. The io signature with be "0", "0" if no pad source is present. @return a string tuple of type, num_ports, port_size @@ -74,7 +72,7 @@ class FlowGraph(_FlowGraph): return self._get_io_signature('pad_source') def get_output_signature(self): - """! + """ Get the io signature for the output side of this flow graph. The io signature with be "0", "0" if no pad sink is present. @return a string tuple of type, num_ports, port_size @@ -82,7 +80,7 @@ class FlowGraph(_FlowGraph): return self._get_io_signature('pad_sink') def get_imports(self): - """! + """ Get a set of all import statments in this flow graph namespace. @return a set of import statements """ @@ -91,7 +89,7 @@ class FlowGraph(_FlowGraph): return imports def get_variables(self): - """! + """ Get a list of all variables in this flow graph namespace. Exclude paramterized variables. @return a sorted list of variable blocks in order of dependency (indep -> dep) @@ -111,7 +109,7 @@ class FlowGraph(_FlowGraph): return variables def get_parameters(self): - """! + """ Get a list of all paramterized variables in this flow graph namespace. @return a list of paramterized variables """ @@ -119,7 +117,7 @@ class FlowGraph(_FlowGraph): return parameters def evaluate(self, expr): - """! + """ Evaluate the expression. @param expr the string expression @throw Exception bad expression @@ -152,4 +150,3 @@ class FlowGraph(_FlowGraph): #evaluate e = eval(expr, self.n, self.n) return e - diff --git a/grc/src/grc_gnuradio/Generator.py b/grc/src/platforms/python/Generator.py index 2c84edb3f..bd3d69cc2 100644 --- a/grc/src/grc_gnuradio/Generator.py +++ b/grc/src/platforms/python/Generator.py @@ -16,20 +16,21 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.Generator -#Create python based flow graphs. import os import subprocess from Cheetah.Template import Template from utils import expr_utils -from Constants import * +from Constants import \ + TOP_BLOCK_FILE_MODE, HIER_BLOCK_FILE_MODE, \ + HIER_BLOCKS_LIB_DIR, PYEXEC, \ + FLOW_GRAPH_TEMPLATE from utils import convert_hier class Generator(object): def __init__(self, flow_graph, file_path): - """! + """ Initialize the generator object. Determine the file to generate. @param flow_graph the flow graph object @@ -39,7 +40,7 @@ class Generator(object): self._generate_options = self._flow_graph.get_option('generate_options') if self._generate_options == 'hb': self._mode = HIER_BLOCK_FILE_MODE - dirname = HIER_BLOCKS_LIB_PATH + dirname = HIER_BLOCKS_LIB_DIR else: self._mode = TOP_BLOCK_FILE_MODE dirname = os.path.dirname(file_path) @@ -57,7 +58,7 @@ class Generator(object): os.chmod(self.get_file_path(), self._mode) def get_popen(self): - """! + """ Execute this python flow graph. @return a popen object """ @@ -69,7 +70,7 @@ class Generator(object): return p def __str__(self): - """! + """ Convert the flow graph to python code. @return a string of python code """ @@ -131,4 +132,3 @@ class Generator(object): #build the template t = Template(open(FLOW_GRAPH_TEMPLATE, 'r').read(), namespace) return str(t) - diff --git a/grc/src/platforms/python/Makefile.am b/grc/src/platforms/python/Makefile.am new file mode 100644 index 000000000..e5845d0ec --- /dev/null +++ b/grc/src/platforms/python/Makefile.am @@ -0,0 +1,51 @@ +# +# Copyright 2008 Free Software Foundation, Inc. +# +# This file is part of GNU Radio +# +# GNU Radio is free software; you can redistribute it and/or modify +# it under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3, or (at your option) +# any later version. +# +# GNU Radio is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with GNU Radio; see the file COPYING. If not, write to +# the Free Software Foundation, Inc., 51 Franklin Street, +# Boston, MA 02110-1301, USA. +# + +include $(top_srcdir)/grc/Makefile.inc + +SUBDIRS = utils + +ourpythondir = $(grc_src_prefix)/platforms/python + +ourpython_PYTHON = \ + Block.py \ + Connection.py \ + Constants.py \ + FlowGraph.py \ + Generator.py \ + Param.py \ + Platform.py \ + Port.py \ + __init__.py + +BUILT_SOURCES = Constants.py + +Constants.py: Makefile $(srcdir)/Constants.py.in + sed \ + -e 's|@PYTHONW[@]|$(PYTHONW)|g' \ + -e 's|@datadir[@]|$(grc_python_data_dir)|g' \ + -e 's|@blocksdir[@]|$(grc_python_blocks_dir)|g' \ + -e 's|@docdir[@]|$(gr_docdir)|g' \ + $(srcdir)/Constants.py.in > $@ + +EXTRA_DIST = Constants.py.in + +MOSTLYCLEANFILES = $(BUILT_SOURCES) diff --git a/grc/src/grc_gnuradio/Param.py b/grc/src/platforms/python/Param.py index 1f5b967a6..ed5c64063 100644 --- a/grc/src/grc_gnuradio/Param.py +++ b/grc/src/platforms/python/Param.py @@ -16,11 +16,9 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.Param -#Flow graph block parameters. from utils import expr_utils -from grc.elements.Param import Param as _Param +from .. base.Param import Param as _Param import os class Param(_Param): @@ -39,7 +37,7 @@ class Param(_Param): ] def get_hide(self): - """! + """ Get the hide value from the base class. If hide was empty, and this is a type controller, set hide to part. If hide was empty, and this is an id of a non variable, set hide to part. @@ -57,7 +55,7 @@ class Param(_Param): return hide def evaluate(self): - """! + """ Evaluate the value. @return evaluated type """ @@ -221,7 +219,7 @@ class Param(_Param): else: raise TypeError, 'Type "%s" not handled'%t def to_code(self): - """! + """ Convert the value to code. @return a string representing the code """ @@ -246,10 +244,9 @@ class Param(_Param): return v def get_all_params(self, type): - """! + """ Get all the params from the flowgraph that have the given type. @param type the specified type @return a list of params """ return sum([filter(lambda p: p.get_type() == type, block.get_params()) for block in self.get_parent().get_parent().get_blocks()], []) - diff --git a/grc/src/grc_gnuradio/Platform.py b/grc/src/platforms/python/Platform.py index 5512940c0..c31701e0e 100644 --- a/grc/src/grc_gnuradio/Platform.py +++ b/grc/src/platforms/python/Platform.py @@ -16,24 +16,25 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.Platform -#Gnuradio python specific platform. import os -from grc.Constants import FLOW_GRAPH_FILE_EXTENSION -from grc.elements.Platform import Platform as _Platform +from .. base.Constants import FLOW_GRAPH_FILE_EXTENSION +from .. base.Platform import Platform as _Platform from FlowGraph import FlowGraph as _FlowGraph from Connection import Connection as _Connection from Block import Block as _Block from Port import Source,Sink from Param import Param as _Param from Generator import Generator -from Constants import * +from Constants import \ + HIER_BLOCKS_LIB_DIR, BLOCK_DTD, \ + BLOCK_TREE, DEFAULT_FLOW_GRAPH, \ + BLOCKS_DIR class Platform(_Platform): def __init__(self, block_paths_internal_only=[], block_paths_external=[]): - """! + """ Make a platform for gnuradio. The internal only list will replace the current block path. @param block_paths_internal_only a list of blocks internal to this platform @@ -42,7 +43,7 @@ class Platform(_Platform): #ensure hier dir if not os.path.exists(HIER_BLOCKS_LIB_DIR): os.mkdir(HIER_BLOCKS_LIB_DIR) #handle internal/only - if block_paths_internal_only: + if block_paths_internal_only: block_paths = map(lambda b: os.path.join(BLOCKS_DIR, b), ['options.xml'] + block_paths_internal_only) else: block_paths = [BLOCKS_DIR] #handle external @@ -70,4 +71,3 @@ class Platform(_Platform): Source = Source Sink = Sink Param = _Param - diff --git a/grc/src/grc_gnuradio/Port.py b/grc/src/platforms/python/Port.py index 3981df7f0..93fa087eb 100644 --- a/grc/src/grc_gnuradio/Port.py +++ b/grc/src/platforms/python/Port.py @@ -16,12 +16,9 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.Port -#Flow graph block port (source or sink). -from grc.elements.Port import Port as _Port -from grc import Utils -from grc.Constants import MAX_NUM_PORTS +from .. base.Port import Port as _Port +from ... import utils class Port(_Port): @@ -35,9 +32,9 @@ class Port(_Port): @param n the nested odict @return a new port """ - vlen = Utils.exists_or_else(n, 'vlen', '1') - nports = Utils.exists_or_else(n, 'nports', '') - optional = Utils.exists_or_else(n, 'optional', '') + vlen = utils.exists_or_else(n, 'vlen', '1') + nports = utils.exists_or_else(n, 'nports', '') + optional = utils.exists_or_else(n, 'optional', '') #build the port _Port.__init__( self, @@ -70,7 +67,7 @@ class Port(_Port): if not nports: return '' try: nports = int(self.get_parent().get_parent().evaluate(nports)) - assert(0 < nports <= MAX_NUM_PORTS) + assert 0 < nports return nports except: return 1 @@ -101,7 +98,7 @@ class Port(_Port): except: return _Port.get_color(self) def is_empty(self): - """! + """ Is this port empty? An empty port has no connections. Not empty of optional is set. diff --git a/grc/src/platforms/python/__init__.py b/grc/src/platforms/python/__init__.py new file mode 100644 index 000000000..8b1378917 --- /dev/null +++ b/grc/src/platforms/python/__init__.py @@ -0,0 +1 @@ + diff --git a/grc/src/grc_gnuradio/utils/Makefile.am b/grc/src/platforms/python/utils/Makefile.am index 01020139e..b12e51d8e 100644 --- a/grc/src/grc_gnuradio/utils/Makefile.am +++ b/grc/src/platforms/python/utils/Makefile.am @@ -19,12 +19,12 @@ # Boston, MA 02110-1301, USA. # -include $(top_srcdir)/Makefile.common +include $(top_srcdir)/grc/Makefile.inc -ourpythondir = $(pythondir)/grc_gnuradio/utils +ourpythondir = $(grc_src_prefix)/platforms/python/utils ourpython_PYTHON = \ - __init__.py \ convert_hier.py \ expr_utils.py \ - extract_docs.py + extract_docs.py \ + __init__.py diff --git a/grc/src/platforms/python/utils/__init__.py b/grc/src/platforms/python/utils/__init__.py new file mode 100644 index 000000000..8b1378917 --- /dev/null +++ b/grc/src/platforms/python/utils/__init__.py @@ -0,0 +1 @@ + diff --git a/grc/src/grc_gnuradio/utils/convert_hier.py b/grc/src/platforms/python/utils/convert_hier.py index 747d2f445..495358984 100644 --- a/grc/src/grc_gnuradio/utils/convert_hier.py +++ b/grc/src/platforms/python/utils/convert_hier.py @@ -16,12 +16,10 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.utils.convert_hier -#Utility functions to convert a grc hier block to an xml wrapper -from grc_gnuradio.Constants import BLOCK_DTD -from grc import ParseXML -from grc.Utils import odict +from .. Constants import BLOCK_DTD +from .... utils import ParseXML +from .... utils import odict def convert_hier(flow_graph, python_file): #extract info from the flow graph diff --git a/grc/src/grc_gnuradio/utils/expr_utils.py b/grc/src/platforms/python/utils/expr_utils.py index 9c729fb87..40700993d 100644 --- a/grc/src/grc_gnuradio/utils/expr_utils.py +++ b/grc/src/platforms/python/utils/expr_utils.py @@ -16,14 +16,12 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.utils.expr_utils -#Utility functions to comprehend variable expressions. import string VAR_CHARS = string.letters + string.digits + '_' class graph(object): - """! + """ Simple graph structure held in a dictionary. """ @@ -52,7 +50,7 @@ class graph(object): def get_edges(self, node_key): return self._graph[node_key] def expr_split(expr): - """! + """ Split up an expression by non alphanumeric characters, including underscore. Leave strings in-tact. #TODO ignore escaped quotes, use raw strings. @@ -78,7 +76,7 @@ def expr_split(expr): return filter(lambda t: t, toks) def expr_prepend(expr, vars, prepend): - """! + """ Search for vars in the expression and add the prepend. @param expr an expression string @param vars a list of variable names @@ -91,7 +89,7 @@ def expr_prepend(expr, vars, prepend): return ''.join(expr_splits) def get_variable_dependencies(expr, vars): - """! + """ Return a set of variables used in this expression. @param expr an expression string @param vars a list of variable names @@ -101,7 +99,7 @@ def get_variable_dependencies(expr, vars): return set(filter(lambda v: v in expr_toks, vars)) def get_graph(exprs): - """! + """ Get a graph representing the variable dependencies @param exprs a mapping of variable name to expression @return a graph of variable deps @@ -116,7 +114,7 @@ def get_graph(exprs): return var_graph def sort_variables(exprs): - """! + """ Get a list of variables in order of dependencies. @param exprs a mapping of variable name to expression @return a list of variable names diff --git a/grc/src/grc_gnuradio/utils/extract_docs.py b/grc/src/platforms/python/utils/extract_docs.py index 55c7b7834..dfc0b7e97 100644 --- a/grc/src/grc_gnuradio/utils/extract_docs.py +++ b/grc/src/platforms/python/utils/extract_docs.py @@ -16,10 +16,8 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc_gnuradio.utils.extract_docs -#Extract documentation from the gnuradio doxygen files. -from grc_gnuradio.Constants import DOCS_DIR +from .. Constants import DOCS_DIR from lxml import etree import os @@ -30,7 +28,7 @@ DOXYGEN_BRIEFDESC_BLKS2_XPATH = '/doxygen/compounddef/sectiondef[@kind="public-f DOXYGEN_DETAILDESC_BLKS2_XPATH = '/doxygen/compounddef/sectiondef[@kind="public-func"]/memberdef/detaileddescription' def extract_txt(xml, parent_text=None): - """! + """ Recursivly pull the text out of an xml tree. @param xml the xml tree @param parent_text the text of the parent element @@ -43,7 +41,7 @@ def extract_txt(xml, parent_text=None): ) + tail def is_match(key, file): - """! + """ Is the block key a match for the given file name? @param key block key @param file the xml file name @@ -73,7 +71,7 @@ def is_match(key, file): return True def extract(key): - """! + """ Extract the documentation from the doxygen generated xml files. If multiple files match, combine the docs. @param key the block key diff --git a/grc/src/grc/elements/Makefile.am b/grc/src/utils/Makefile.am index 2b97c9771..c00102f98 100644 --- a/grc/src/grc/elements/Makefile.am +++ b/grc/src/utils/Makefile.am @@ -19,16 +19,11 @@ # Boston, MA 02110-1301, USA. # -include $(top_srcdir)/Makefile.common +include $(top_srcdir)/grc/Makefile.inc -ourpythondir = $(pythondir)/grc/elements +ourpythondir = $(grc_src_prefix)/utils ourpython_PYTHON = \ - __init__.py \ - Block.py \ - Connection.py \ - Element.py \ - FlowGraph.py \ - Param.py \ - Platform.py \ - Port.py + converter.py \ + ParseXML.py \ + __init__.py diff --git a/grc/src/grc/ParseXML.py b/grc/src/utils/ParseXML.py index cf6ce8301..71f8c5279 100644 --- a/grc/src/grc/ParseXML.py +++ b/grc/src/utils/ParseXML.py @@ -16,16 +16,14 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.ParseXML -#Parse xml files to nested data and vice-versa. from lxml import etree -from Utils import odict +from .. utils import odict XMLSyntaxError = etree.XMLSyntaxError def validate_dtd(xml_file, dtd_file=None): - """! + """ Validate an xml file against its dtd. @param xml_file the xml file @param dtd_file the optional dtd file @@ -43,7 +41,7 @@ def validate_dtd(xml_file, dtd_file=None): raise XMLSyntaxError, '\n'.join(map(str, parser.error_log.filter_from_errors())) def from_file(xml_file): - """! + """ Create nested data from an xml file using the from xml helper. @param xml_file the xml file path @return the nested data @@ -52,7 +50,7 @@ def from_file(xml_file): return _from_file(xml) def _from_file(xml): - """! + """ Recursivly parse the xml tree into nested data format. @param xml the xml tree @return the nested data @@ -71,7 +69,7 @@ def _from_file(xml): return odict({tag: nested_data}) def to_file(nested_data, xml_file): - """! + """ Write an xml file and use the to xml helper method to load it. @param nested_data the nested data @param xml_file the xml file path @@ -80,7 +78,7 @@ def to_file(nested_data, xml_file): open(xml_file, 'w').write(etree.tostring(xml, xml_declaration=True, pretty_print=True)) def _to_file(nested_data): - """! + """ Recursivly parse the nested data into xml tree format. @param nested_data the nested data @return the xml tree filled with child nodes diff --git a/grc/src/grc/Utils.py b/grc/src/utils/__init__.py index 1cc71b42b..21af4a8be 100644 --- a/grc/src/grc/Utils.py +++ b/grc/src/utils/__init__.py @@ -16,8 +16,6 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.gui.Utils -#Utility methods and classes. from UserDict import DictMixin @@ -56,4 +54,3 @@ def listify(d, key): obj = exists_or_else(d, key, []) if isinstance(obj, list): return obj return [obj] - diff --git a/grc/src/grc/converter.py b/grc/src/utils/converter.py index a69163e26..d0ff94e66 100644 --- a/grc/src/grc/converter.py +++ b/grc/src/utils/converter.py @@ -16,18 +16,16 @@ You should have received a copy of the GNU General Public License along with this program; if not, write to the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA """ -##@package grc.converter -#convert old flow graph file format to new format -from grc.Constants import FLOW_GRAPH_DTD -from grc import ParseXML, Utils -from grc.Utils import odict +from .. platforms.base.Constants import FLOW_GRAPH_DTD +import ParseXML +from .. utils import odict from lxml import etree import difflib import os def _make_param(key, value): - """! + """ Make a paramater dict from the key/value pair. @param key the key @param value the value @@ -39,7 +37,7 @@ def _make_param(key, value): return param def _get_blocks(blocks, tag): - """! + """ Get a list of blocks with the tag. @param blocks the old block list @param tag the tag name @@ -48,7 +46,7 @@ def _get_blocks(blocks, tag): return filter(lambda b: b['tag'] == tag, blocks) def _get_params(block): - """! + """ Get a list of params. @param block the old block @retun a list of params @@ -58,7 +56,7 @@ def _get_params(block): return params def _convert_id(id): - """! + """ Convert an old id to a new safe id. Replace spaces with underscores. Lower case the odl id. @@ -67,7 +65,7 @@ def _convert_id(id): return id.lower().replace(' ', '_') def convert(file_path, platform): - """! + """ Convert the flow graph to the new format. Make a backup of the old file. Save a reformated flow graph to the file path. @@ -146,7 +144,7 @@ def convert(file_path, platform): ############################################################ # conversion - variables ############################################################ - x = 100 + x = 100 for variable in variables: key = variable['key'] value = variable['value'] @@ -247,4 +245,3 @@ def convert(file_path, platform): os.rename(file_path, file_path+'.bak') #save new flow graph to file path ParseXML.to_file({'flow_graph': new_n}, file_path) - |