Index: misc/tools/plotcsv/plotcsv.py
===================================================================
--- misc/tools/plotcsv/plotcsv.py	(revision 6338)
+++ misc/tools/plotcsv/plotcsv.py	(revision 6341)
@@ -15,4 +15,82 @@
 import pylab
 
+try:
+    import wx
+except ImportError:
+    import tkinter_error
+    msg = ('Sorry, you have to install WxPython.\n'
+           'Get it from either:\n'
+           r'   N:\georisk\downloads\event_selection, or' '\n'
+           '   [http://www.wxpython.org/download.php#binaries].')
+    tkinter_error.tkinter_error(msg)
+    print msg
+    sys.exit(1)
+
+Imported_PyEmbeddedImage = True
+try:
+    from wx.lib.embeddedimage import PyEmbeddedImage
+except ImportError:
+    Imported_PyEmbeddedImage = False
+
+
+# program name and version
+APP_NAME = 'plotcsv'
+APP_VERSION = '0.1'
+
+# name of the configuration filename
+# GUI values are saved in this file for next time
+ConfigFilename = '%s.cfg' % APP_NAME
+
+# GUI definitions
+BUTTON_WIDTH = 100
+BUTTON_HEIGHT = 30
+
+MARGIN = 10
+
+LAB_CTRL_OFFSET = 3
+
+BOX_WIDTH = 400
+BOX_HEIGHT = 360
+BOX_CSV_WIDTH = 400
+BOX_CSV_HEIGHT = 265
+BOX_PLOT_WIDTH = 400
+BOX_PLOT_HEIGHT = 90
+
+TXT_CSVFILE_WIDTH = 390
+TXT_CSVFILE_HEIGHT = 200
+
+COLLAB_X_OFFSET = 20
+
+CHBOX_HEIGHT = 30
+CHBOX_WIDTH = 100
+
+FORM_WIDTH = BOX_WIDTH + 15
+FORM_HEIGHT = 405
+
+START_YOFFSET = 7
+OUT_TEXT_XOFFSET = 8
+OUT_TEXT_YOFFSET = 11
+OUTPUT_BOX_HEIGHT = 45
+
+GEN_YOFFSET = 15
+GEN_DELTAY = 15
+GEN_LABELXOFFSET = 5
+GEN_TEXTXOFFSET = BOX_WIDTH/2 + GEN_LABELXOFFSET + 10
+
+TEXTLIST_WIDTH = BOX_WIDTH - 10
+TEXTLIST_HEIGHT = 200
+
+CTL_WIDTH = BOX_WIDTH / 2
+CTL_HEIGHT = 22
+
+DOUBLE_BUTTON_OFFSET = 8
+
+COMBO_FUDGE = 2
+
+# Copies of various parameters
+Region = ''
+GaugeNumber = ''
+MinimumHeight = ''
+MaximumHeight = ''
 
 # Flag strings - keys in the 'options' dictionary
@@ -26,4 +104,28 @@
 X_LABEL = 'x_label'
 Y_LABEL = 'y_label'
+
+
+################################################################################
+# This code was generated by img2py.py
+# Embed the ICON image here, so we don't need an external *.ico file.
+################################################################################
+
+if Imported_PyEmbeddedImage:
+    def getIcon():
+        return PyEmbeddedImage(
+    "iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAYAAABzenr0AAAABHNCSVQICAgIfAhkiAAAApxJ"
+    "REFUWIXtlr9O40AQh2edWwsKJFAarGtcRaElJWkoo4TGZegocqLME6TOC6CtaWjCFXRUfgJE"
+    "xStsiivuKiQ4ND8Kx/bu+k+cUKRhpC0ie+f7sjs7a0FEoB3GDyIiYDcOQgjydkI24lvgW2Bj"
+    "gctLolaLaG+P6OiI6PCQSIh89HpEy+VmOdE0lAKI1o8oArSuycMKAQegVQ9qDJeymUCdhGIF"
+    "yRLE1FzAhZ+dATc3wN0d8PiYg9z3XAkLbgl0u4DnAePxWvja5XXen0zK4RFHhoA5lNoabs4z"
+    "Uw4finDN2hAIw/xtKQGltoanMZut5k4U6K0IB2AIaJ0QVrQPT+LaU1vD0xg+2PDuSwJXCggC"
+    "UwAoSLyTxC9SpfAFLxBwAJ99THlavg1uwS0i0LHGcGiurHMKbucav0Uu8V9I/JsrK7FmjRM+"
+    "yRL77CPmuBbefUngxeNqCKR7HpDGPUWFmkjhEUf5v1qNkMNMoqzaNWtMJsU+kQmMx/bDq4HG"
+    "68CW0LdzC97iFtrctiSmPC2Fpzvc7yenvd9PfmcC+/s56/x8tedGTehjQnQvssSSJRQrxBwj"
+    "5LCwIi68KqwV8LykHz0/mxuuoa8GiBZ5YvnhQXFeF2USTeCWQFVo1oheBzn8jaCuPatZpRId"
+    "7sBnHyMeJXCtgaen2vNbK+AWnHwXUJNiYZZP1slylt1Sp6eZVKVAAc4S6u/c6hO1Em7JV1yV"
+    "pQKl8HTPnWZVKpH14PX3dUGgFm4ub5WEewvNZvZc54KxBBrB6ySmU+DgoHgPu2FIZAIbwask"
+    "zNHrrf9oCIxPMrO3N4LXSYQhEMeNpmcCKVywaA43JUYjwPeBTqcx3BIIOYTHHi74YjP4F4OI"
+    "IIgI9JOI2kS0JKI/m33TfzU+ASG0bvT61fpzAAAAAElFTkSuQmCC")
 
 
@@ -132,57 +234,201 @@
 
 
-##
-# @brief Help for the befuddled user.
-def usage():
-    print 'usage: %s <options> <filename>' % (ProgName)
-    print 'where <filename> is the path to the data file to plot'
-    print '  and <options>  is zero or more of:'
-    print '                   -x <datacol> where <datacol> is a column specifier,'
-    print '                   -y <datacol>     either a number or a header string'
-    print '                   -v <range>   force a range in Y axis values, of the form'
-    print '                                    <min>,<max>, eq, "-5,10"'
-    print '                   -s <min,max> sets PNG output picture size'
-    sys.exit(10)
+class MyFrame(wx.Frame):
+    def __init__(self, parent, id, title, pos=wx.DefaultPosition,
+                    size=wx.DefaultSize, style=wx.DEFAULT_FRAME_STYLE):
+        # Make the frame
+        wx.Frame.__init__(self, parent, id, title, pos=(50, 50),
+                            size=(FORM_WIDTH, FORM_HEIGHT),
+                            style=(wx.DEFAULT_FRAME_STYLE &
+                                   ~ (wx.RESIZE_BOX | wx.MAXIMIZE_BOX |
+                                      wx.RESIZE_BORDER)))
+
+        p = self.panel = wx.Panel(self, -1)
+
+        if Imported_PyEmbeddedImage:
+            tsunami = getIcon()
+            icon = tsunami.GetIcon()
+            self.SetIcon(icon)
+        
+        self.Center()
+        self.Show(True)
+
+        # start laying out controls
+        Y_OFFSET = START_YOFFSET
+        wx.StaticBox(p, -1, 'CSV files', (3, Y_OFFSET),
+                     size=(BOX_CSV_WIDTH, BOX_CSV_HEIGHT))
+
+##        wx.StaticText(p, -1, 'Minimum wave height',
+##                      pos=(GEN_LABELXOFFSET, Y_OFFSET),
+##                      size=(CTL_WIDTH, CTL_HEIGHT), style=wx.ALIGN_RIGHT)
+##        self.txtMinH = wx.TextCtrl(p, -1, size=(100, 20),
+##                                   pos=(GEN_TEXTXOFFSET, Y_OFFSET))
+        Y_OFFSET += GEN_DELTAY 
+
+##        self.lstGenerate = wx.ListCtrl(p, -1, pos=(8, Y_OFFSET),
+##                                       size=(TEXTLIST_WIDTH,TEXTLIST_HEIGHT),
+##                                       style=wx.LC_SINGLE_SEL)
+##        self.txtCSVFiles = wx.TextCtrl(p, -1,
+##                        "Here is a looooooooooooooong line of text set in the control.\n\n"
+##                        "The quick brown fox jumped over the lazy dog...",
+##                       pos=(8, Y_OFFSET), size=(TXT_CSVFILE_WIDTH,TXT_CSVFILE_HEIGHT), style=wx.TE_MULTILINE|wx.TE_PROCESS_ENTER)
+        self.txtCSVFiles = wx.ListBox(p, -1, pos=(8, Y_OFFSET), size=(TXT_CSVFILE_WIDTH,TXT_CSVFILE_HEIGHT))
+        Y_OFFSET += TXT_CSVFILE_HEIGHT + MARGIN 
+        x = FORM_WIDTH/2 - BUTTON_WIDTH - DOUBLE_BUTTON_OFFSET
+        self.btnAddCSVFile = wx.Button(p, label="Add", pos=(x, Y_OFFSET),
+                                     size=(100, BUTTON_HEIGHT))
+        x = FORM_WIDTH/2 + DOUBLE_BUTTON_OFFSET
+        self.btnDelCSVFile = wx.Button(p, label="Delete", pos=(x, Y_OFFSET),
+                                     size=(100, BUTTON_HEIGHT))
+        Y_OFFSET += BUTTON_HEIGHT + MARGIN 
+
+        wx.StaticBox(p, -1, 'Plot details', (3, Y_OFFSET),
+                     size=(BOX_PLOT_WIDTH, BOX_PLOT_HEIGHT))
+        Y_OFFSET += GEN_DELTAY
+        wx.StaticText(p, -1, 'X-Column',
+                      pos=(COLLAB_X_OFFSET, Y_OFFSET+LAB_CTRL_OFFSET), style=wx.ALIGN_LEFT)
+        self.cbXColHdr = wx.ComboBox(p, -1, pos=(COLLAB_X_OFFSET+50, Y_OFFSET),
+                                     size=(80, -1), style=wx.CB_DROPDOWN)
+        wx.StaticText(p, -1, 'Y-Column',
+                      pos=(FORM_WIDTH/2+COLLAB_X_OFFSET,
+                           Y_OFFSET+LAB_CTRL_OFFSET), style=wx.ALIGN_LEFT)
+        x = FORM_WIDTH/2 + COLLAB_X_OFFSET
+        self.cbYColHdr = wx.ComboBox(p, -1, pos=(x+50, Y_OFFSET),
+                                     size=(80, -1), style=wx.CB_DROPDOWN)
+
+        Y_OFFSET += BUTTON_HEIGHT + MARGIN
+        x = FORM_WIDTH/2 - BUTTON_WIDTH/2
+        self.btnPlote = wx.Button(p, label="Plot", pos=(x, Y_OFFSET),
+                                     size=(100, BUTTON_HEIGHT))
+
+
+
+
+
+##        wx.StaticText(p, -1, 'Maximum wave height',
+##                      pos=(GEN_LABELXOFFSET, Y_OFFSET),
+##                      size=(CTL_WIDTH, CTL_HEIGHT), style=wx.ALIGN_RIGHT)
+##        self.chXColHdr = wx.Choice(p, -1, size=(CHBOX_WIDTH, CHBOX_HEIGHT),
+##                                   pos=(10,Y_OFFSET))
+
+
+
+
+
+
+##        wx.StaticText(p, -1, 'Maximum wave height',
+##                      pos=(GEN_LABELXOFFSET, Y_OFFSET),
+##                      size=(CTL_WIDTH, CTL_HEIGHT), style=wx.ALIGN_RIGHT)
+##        self.txtMaxH = wx.TextCtrl(p, -1, size=(100, 20),
+##                                   pos=(GEN_TEXTXOFFSET, Y_OFFSET))
+##        Y_OFFSET += GEN_DELTAY 
+##        x = FORM_WIDTH/2 - BUTTON_WIDTH/2
+##        self.btnGenerate = wx.Button(p, label="List",
+##                                     pos=(x, Y_OFFSET),
+##                                     size=(100, BUTTON_HEIGHT))
+##        Y_OFFSET += GEN_DELTAY + BUTTON_HEIGHT/2
+##
+##        self.lstGenerate = wx.ListCtrl(p, -1, pos=(8, Y_OFFSET),
+##                                       size=(TEXTLIST_WIDTH,TEXTLIST_HEIGHT),
+##                                       style=wx.LC_REPORT|wx.LC_SINGLE_SEL)
+##        
+##        Y_OFFSET += TEXTLIST_HEIGHT + 20
+##        self.Bind(wx.EVT_BUTTON, self.GenerateClick, self.btnGenerate)
+##        self.lstGenerate.Bind(wx.EVT_LIST_ITEM_SELECTED,
+##                              self.OnItemSelected, self.lstGenerate)
+##
+##        # start laying out get_multimux controls
+##        wx.StaticBox(p, -1, 'multimux_grid', (3, Y_OFFSET),
+##                     size=(BOX_WIDTH, BOX2_HEIGHT))
+##        Y_OFFSET += 18
+##        wx.StaticText(p, -1, 'Quake ID', pos=(GEN_LABELXOFFSET, Y_OFFSET),
+##                      size=(CTL_WIDTH, CTL_HEIGHT), style=wx.ALIGN_RIGHT)
+##        self.txtQuakeID = wx.TextCtrl(p, -1, size=(100, 20),
+##                                      pos=(GEN_TEXTXOFFSET, Y_OFFSET))
+##        Y_OFFSET += GEN_DELTAY 
+##        x = FORM_WIDTH/2 - BUTTON_WIDTH - DOUBLE_BUTTON_OFFSET
+##        self.btnMultimux = wx.Button(p, label="Multimux", pos=(x, Y_OFFSET),
+##                                     size=(100, BUTTON_HEIGHT))
+##        x = FORM_WIDTH/2 + DOUBLE_BUTTON_OFFSET
+##        self.btnGrid = wx.Button(p, label="Grid", pos=(x, Y_OFFSET),
+##                                     size=(100, BUTTON_HEIGHT))
+##        Y_OFFSET += GEN_DELTAY + BUTTON_HEIGHT/2
+##        self.lstMultimux = wx.ListCtrl(p, -1, pos=(8, Y_OFFSET),
+##                                       size=(TEXTLIST_WIDTH,TEXTLIST_HEIGHT),
+##                                       style=wx.LC_REPORT|wx.LC_SINGLE_SEL)
+##        Y_OFFSET += TEXTLIST_HEIGHT + 20
+##        self.Bind(wx.EVT_BUTTON, self.MultimuxClick, self.btnMultimux)
+##        self.Bind(wx.EVT_BUTTON, self.GridClick, self.btnGrid)
+
+        self.Bind(wx.EVT_CLOSE, self.doStateSave)
+        self.doStateRestore()
+
+    def doStateSave(self, event):
+        """
+        Save state here.
+        """
+##        self.cfg['OutputDirectory'] = self.txtOutputDir.GetValue()
+##        self.cfg['Region'] = self.cbRegion.GetValue()
+##        self.cfg['GaugeNumber'] = self.txtTGN.GetValue()
+##        self.cfg['MinimumHeight'] = self.txtMinH.GetValue()
+##        self.cfg['MaximumHeight'] = self.txtMaxH.GetValue()
+##        self.cfg.save()
+        
+        event.Skip(True)
+
+    def doStateRestore(self):
+        """
+        Restore state here - globals have been set and tested sane
+        """
+##        global Region, GaugeNumber, MinimumHeight, MaximumHeight
+##
+##        cfg = Config(ConfigFilename)
+##        output_dir = cfg['OutputDirectory']
+##        Region = cfg['Region']
+##        GaugeNumber = cfg['GaugeNumber']
+##        if GaugeNumber:
+##            GaugeNumber = int(GaugeNumber)
+##        MinimumHeight = cfg['MinimumHeight']
+##        if MinimumHeight:
+##            MinimumHeight = float(MinimumHeight)
+##        MaximumHeight = cfg['MaximumHeight']
+##        if MaximumHeight:
+##            MaximumHeight = float(MaximumHeight)
+##
+##        self.cfg = cfg
+##
+##        region_name = None
+##        for (name, dir) in Regions:
+##            if name == Region:
+##                region_name = name
+##        if not region_name:
+##            Region = ''
+##
+##        if output_dir:
+##            self.txtOutputDir.WriteText(output_dir)
+##        self.cbRegion.SetStringSelection(Region)
+##        if GaugeNumber:
+##            self.txtTGN.WriteText(str(GaugeNumber))
+##        if MinimumHeight:
+##            self.txtMinH.WriteText(str(MinimumHeight))
+##        if MaximumHeight:
+##            self.txtMaxH.WriteText(str(MaximumHeight))
+        
+    def error(self, msg):
+        dlg = wx.MessageDialog(self, msg, 'Error',
+                               wx.OK | wx.ICON_INFORMATION)
+        dlg.ShowModal()
+        dlg.Destroy()
+
+        
+################################################################################
+# Code to do the GUI
+################################################################################
 
 if __name__ == '__main__':
-    # dictionary to convert option string to internal name
-    of_dict = { '-x': X_DATACOL,
-                '-y': Y_DATACOL,
-                '-s': SIZE,
-                '-v': Y_RANGE }
-
-    # set name of the program (for error reporting)
-    global ProgName
-    try:
-        ProgName = os.path.basename(sys.argv[0])
-    except:
-        pass
-
-    # get options
-    opt_dict = {}
-    params = sys.argv[1:]
-    (opts, args) = getopt.gnu_getopt(params, 'x:y:s:v:')
-    if len(args) != 1:
-        usage()
-    for (o, v) in opts:
-        try:
-            opt_dict[of_dict[o]] = v.lower()
-        except:
-            usage()
-
-    # get name of data file
-    if len(args) != 1:
-        usage()
-    filename = args[0]
-    (filename_minus, _) = filename.split('.', 1)
-
-    # set default option values
-    opt_dict[X_DATACOL] = opt_dict.get(X_DATACOL, 0)
-    opt_dict[Y_DATACOL] = opt_dict.get(Y_DATACOL, 1)
-    opt_dict[SIZE] = opt_dict.get(SIZE, '800,600')
-#    opt_dict[X_RANGE] = opt_dict.get(X_RANGE, None)
-    opt_dict[Y_RANGE] = opt_dict.get(Y_RANGE, None)
-    opt_dict[FILENAME] = filename_minus
-
-    # plot the file
-    plot_file(args[0], opt_dict)
+    app = wx.App()
+    frame = MyFrame(None, -1, '%s %s' % (APP_NAME, APP_VERSION),
+                    size=(FORM_WIDTH, FORM_HEIGHT))
+    app.SetTopWindow(frame)
+    app.MainLoop()
+
