def SetFromDb(self, db, experimentId):
     try:
         experimentController = ExperimentController(db, Experiment, None, None)
         experiment = experimentController.getRecordByKey(experimentId)
         defaultsController = AlgorithmDefaultsController(db, AlgorithmDefaults, None, None)
         defaults = defaultsController.getAll(experiment.algorithm_id)
         for d in defaults:
             self[str(d.parameter_name)] = str(d.default_value)
         configController = ExperimentConfigurationController(db, ExperimentConfiguration, None, None)
         configs = configController.getAll(experimentId)
         for c in configs:
             self[str(c.parameter_name)] = str(c.parameter_value)
         config_file = self.as_config_file(silent=False)
         return config_file
     except Exception as e:
         print e
 def InitCanvas(self):
     global db, algorithmName
     print "before call"
     self.sessionController = PreventionSessionController(db, PreventionSession, None, None)
     self.experimentController = ExperimentController(db, Experiment, None, None)
     experiment = self.experimentController.getDefaultExperiment(algorithmName)
     self.experiment_id = experiment.id
     self.depth_canvas = PreventionDepthCameraCanvas (self.depth_video_panel, 40, "PUDepthCanvas", db, experiment.id)
     w = self.depth_canvas.GetWindow()
     
     #w.SetMinSize(wx.Size(640, 480))
     depthPanelSizer = wx.BoxSizer(wx.VERTICAL)
     depthPanelSizer.Add(w, 0, wx.EXPAND, 0, self.depth_canvas)
     self.depth_video_panel.SetSizer(depthPanelSizer)
     depthPanelSizer.Layout()
     
     self.Layout()
     
     #wx.Sleep(2)
     #print "Canvas ready?  %s" % self.depth_canvas.canvas_.is_ready()
     #print "after call"
     
     while w:
         w.Layout()
         w.Refresh()
         w = w.GetParent()
Пример #3
0
import sys
from PyQt5.QtWidgets import QApplication
from experiment_controller import ExperimentController

if __name__ == '__main__':
    app = QApplication(sys.argv)
    c = ExperimentController()
    c.show_participant_form()
    sys.exit(app.exec_())
class MainFrame(wx.Frame):
    """
    This class implements the main window (or frame) for the Prevention System GUI.
    It defines the window, the menubars, the tabbed notebook panes, and a status line.
    For the Prevention GUI the notebook panes consist of a collection pane and a clinical
    pane. The collection pane will contain a GLCanvas which will display the video from
    the depth camera.
    Methods:
        __init__(*args, **kwds) - creates the widgets in the frame and performs initialization
        __set_properties() - set various properties of the widgets
        __do_layout() - lays out the widgets
        doNewPatient(event) - Menu handler for adding new patients
        doSelectPatient(event) - Menu handler for selecting a patient to record
    """
    def __init__(self, *args, **kwds):
        """
        Creates the widgets in the frame and performs initialization.
        Also, creates and attaches an OpenGL canvas for the camera process to use.
        """
        # begin wxGlade: MainFrame.__init__
        kwds["style"] = wx.DEFAULT_FRAME_STYLE
        wx.Frame.__init__(self, *args, **kwds)
        
        # Menu Bar
        self.main_frame_menubar = wx.MenuBar()
        self.mainFileMenu = wx.Menu()
        self.exitMenuItem = wx.MenuItem(self.mainFileMenu, wx.ID_ANY, _("Exit"), "", wx.ITEM_NORMAL)
        self.mainFileMenu.AppendItem(self.exitMenuItem)
        self.main_frame_menubar.Append(self.mainFileMenu, _("File"))
        self.mainPatientMenu = wx.Menu()
        self.newPatientMenuItem = wx.MenuItem(self.mainPatientMenu, wx.ID_ANY, _("New/Modify..."), "", wx.ITEM_NORMAL)
        self.mainPatientMenu.AppendItem(self.newPatientMenuItem)
        self.selectPatientMenuItem = wx.MenuItem(self.mainPatientMenu, wx.ID_ANY, _("Select..."), "", wx.ITEM_NORMAL)
        self.mainPatientMenu.AppendItem(self.selectPatientMenuItem)
        self.main_frame_menubar.Append(self.mainPatientMenu, _("Patient"))
        self.mainAlgorithmMenu = wx.Menu()
        self.newAlgorithmItem = wx.MenuItem(self.mainAlgorithmMenu, wx.ID_ANY, _("New/Modify/Delete Algorithm..."), "", wx.ITEM_NORMAL)
        self.mainAlgorithmMenu.AppendItem(self.newAlgorithmItem)
        self.newExperimentItem = wx.MenuItem(self.mainAlgorithmMenu, wx.ID_ANY, _("New/Modify/Delete Experiment..."), "", wx.ITEM_NORMAL)
        self.mainAlgorithmMenu.AppendItem(self.newExperimentItem)
        self.main_frame_menubar.Append(self.mainAlgorithmMenu, _("Algorithm"))
        self.mainAdminMenu = wx.Menu()
        self.changePasswordItem = wx.MenuItem(self.mainAdminMenu, wx.ID_ANY, _("Change Password..."), "", wx.ITEM_NORMAL)
        self.mainAdminMenu.AppendItem(self.changePasswordItem)
        self.manageUsersItem = wx.MenuItem(self.mainAdminMenu, wx.ID_ANY, _("Manage Users..."), "", wx.ITEM_NORMAL)
        self.mainAdminMenu.AppendItem(self.manageUsersItem)
        self.accessControlItem = wx.MenuItem(self.mainAdminMenu, wx.ID_ANY, _("Access Control..."), "", wx.ITEM_NORMAL)
        self.mainAdminMenu.AppendItem(self.accessControlItem)
        self.newSystemConfiguration = wx.MenuItem(self.mainAdminMenu, wx.ID_ANY, _("System Configuration..."), "", wx.ITEM_NORMAL)
        self.mainAdminMenu.AppendItem(self.newSystemConfiguration)
        self.main_frame_menubar.Append(self.mainAdminMenu, _("Admin"))
        self.mainHelpMenu = wx.Menu()
        self.main_frame_menubar.Append(self.mainHelpMenu, _("Help"))
        self.SetMenuBar(self.main_frame_menubar)
        # Menu Bar end
        self.main_frame_statusbar = self.CreateStatusBar(1, 0)
        self.panel_1 = wx.Panel(self, wx.ID_ANY)
        self.prevention_notebook = wx.Notebook(self.panel_1, wx.ID_ANY, style=0)
        self.prevention_collection_pane = wx.Panel(self.prevention_notebook, wx.ID_ANY)
        self.depth_video_panel = wx.Panel(self.prevention_collection_pane, wx.ID_ANY)
        self.label_1 = wx.StaticText(self.prevention_collection_pane, wx.ID_ANY, _("Patient"), style=wx.ALIGN_CENTRE)
        self.patient_name = wx.TextCtrl(self.prevention_collection_pane, wx.ID_ANY, _("None"), style=wx.TE_READONLY)
        self.start_button = wx.Button(self.prevention_collection_pane, wx.ID_ANY, _("Start Recording"))
        self.stop_button = wx.Button(self.prevention_collection_pane, wx.ID_ANY, _("Stop Recording"))
        self.olv = FastObjectListView(self.prevention_collection_pane, wx.ID_ANY, style=wx.LC_REPORT|wx.SUNKEN_BORDER)
        self.prevention_clinical_pane = wx.Panel(self.prevention_notebook, wx.ID_ANY)
        self.clinical_label_1 = wx.StaticText(self.prevention_clinical_pane, wx.ID_ANY, _("Prevention Care Reporting"), style=wx.ALIGN_CENTRE)
        self.clinical_container_panel = wx.Panel(self.prevention_clinical_pane, wx.ID_ANY)

        self.__set_properties()
        self.__do_layout()

        self.Bind(wx.EVT_MENU, self.OnExit, self.exitMenuItem)
        self.Bind(wx.EVT_MENU, self.DoAlgorithmList, self.newAlgorithmItem)
        self.Bind(wx.EVT_MENU, self.DoExperimentList, self.newExperimentItem)
        self.Bind(wx.EVT_MENU, self.DoChangePassword, self.changePasswordItem)
        self.Bind(wx.EVT_MENU, self.DoConfigList, self.newSystemConfiguration)
        self.Bind(wx.EVT_BUTTON, self.doStartRecording, self.start_button)
        self.Bind(wx.EVT_BUTTON, self.DoStopRecording, self.stop_button)
        # end wxGlade
        self.currentPatient = None
        self.Bind(wx.EVT_CLOSE, self.OnExit)
        self.Bind(wx.EVT_MENU, self.doNewPatient, self.newPatientMenuItem)
        self.Bind(wx.EVT_MENU, self.doSelectPatient, self.selectPatientMenuItem)
        self.start_button.Disable()
        self.stop_button.Disable()
        # Wrap the ObjectListView in a batch updater
        # self.olv = BatchedUpdate(self.olv, 10)
        self.olv.SetEmptyListMsg("No Turning Events Found")
        self.olv.SetColumns(OlvPatientTurningCols().getColumnDefinitions())
        # ----------
        # ----------

    def __set_properties(self):
        """
        Sets various properties of the widgets
        """
        # begin wxGlade: MainFrame.__set_properties
        self.SetTitle(_("Multi-Modality Portable System for Pressure Ulcer Prevention"))
        self.main_frame_statusbar.SetStatusWidths([-1])
        # statusbar fields
        main_frame_statusbar_fields = [_("frame_1_statusbar")]
        for i in range(len(main_frame_statusbar_fields)):
            self.main_frame_statusbar.SetStatusText(main_frame_statusbar_fields[i], i)
        self.depth_video_panel.SetMinSize((640, 480))
        self.start_button.SetMinSize((100, 23))
        self.stop_button.SetMinSize((100, 23))
        self.prevention_collection_pane.SetFocus()
        self.clinical_label_1.SetFont(wx.Font(14, wx.DEFAULT, wx.NORMAL, wx.BOLD, 0, ""))
        self.prevention_notebook.SetMinSize((844, 1001))
        # end wxGlade

    def __do_layout(self):
        """
        Lays out the widgets in the frame
        """
        # begin wxGlade: MainFrame.__do_layout
        sizer_1 = wx.BoxSizer(wx.VERTICAL)
        sizer_2 = wx.BoxSizer(wx.VERTICAL)
        clinical_pane_sizer = wx.BoxSizer(wx.VERTICAL)
        collection_sizer_1 = wx.BoxSizer(wx.VERTICAL)
        sizer_6 = wx.BoxSizer(wx.HORIZONTAL)
        sizer_3 = wx.BoxSizer(wx.VERTICAL)
        sizer_6.Add(self.depth_video_panel, 0, wx.EXPAND, 0)
        sizer_3.Add((20, 20), 0, 0, 0)
        sizer_3.Add(self.label_1, 0, 0, 0)
        sizer_3.Add(self.patient_name, 0, 0, 0)
        sizer_3.Add((20, 40), 0, 0, 0)
        sizer_3.Add(self.start_button, 0, 0, 2)
        sizer_3.Add((20, 40), 0, 0, 0)
        sizer_3.Add(self.stop_button, 0, 0, 2)
        sizer_6.Add(sizer_3, 1, wx.LEFT | wx.EXPAND, 20)
        collection_sizer_1.Add(sizer_6, 0, wx.LEFT | wx.TOP | wx.EXPAND, 10)
        collection_sizer_1.Add((20, 20), 0, 0, 0)
        collection_sizer_1.Add(self.olv, 1, wx.EXPAND, 0)
        self.prevention_collection_pane.SetSizer(collection_sizer_1)
        clinical_pane_sizer.Add(self.clinical_label_1, 0, wx.ALIGN_CENTER_HORIZONTAL, 0)
        clinical_pane_sizer.Add((20, 20), 0, 0, 0)
        clinical_pane_sizer.Add(self.clinical_container_panel, 1, wx.EXPAND, 0)
        self.prevention_clinical_pane.SetSizer(clinical_pane_sizer)
        self.prevention_notebook.AddPage(self.prevention_collection_pane, _("Collection"))
        self.prevention_notebook.AddPage(self.prevention_clinical_pane, _("Clinical"))
        sizer_2.Add(self.prevention_notebook, 1, wx.EXPAND, 0)
        self.panel_1.SetSizer(sizer_2)
        sizer_1.Add(self.panel_1, 1000, wx.EXPAND, 0)
        self.SetSizer(sizer_1)
        sizer_1.Fit(self)
        self.Layout()
        # end wxGlade
        self.clinical_pane_sizer = clinical_pane_sizer

    def InitCanvas(self):
        global db, algorithmName
        print "before call"
        self.sessionController = PreventionSessionController(db, PreventionSession, None, None)
        self.experimentController = ExperimentController(db, Experiment, None, None)
        experiment = self.experimentController.getDefaultExperiment(algorithmName)
        self.experiment_id = experiment.id
        self.depth_canvas = PreventionDepthCameraCanvas (self.depth_video_panel, 40, "PUDepthCanvas", db, experiment.id)
        w = self.depth_canvas.GetWindow()
        
        #w.SetMinSize(wx.Size(640, 480))
        depthPanelSizer = wx.BoxSizer(wx.VERTICAL)
        depthPanelSizer.Add(w, 0, wx.EXPAND, 0, self.depth_canvas)
        self.depth_video_panel.SetSizer(depthPanelSizer)
        depthPanelSizer.Layout()
        
        self.Layout()
        
        #wx.Sleep(2)
        #print "Canvas ready?  %s" % self.depth_canvas.canvas_.is_ready()
        #print "after call"
        
        while w:
            w.Layout()
            w.Refresh()
            w = w.GetParent()

    def InitMisc(self):
        """
        Method to initialize various misc. items
        """
        global db
        # Set up file director
        self.director = PUFileDirector(self.system_config['BASE_FILE_DIRECTORY'])
        self.director.SetSystemType("prevention")
        # Set up database writer
        self.preventionDatabaseWriter = PreventionDatabaseWriter(db)

    def InitClinicalPane(self):
        global db
        self.prevention_clinical_panel = PreventionClinicalDataDialog(self.clinical_container_panel, db)
        cpsizer = wx.BoxSizer(wx.VERTICAL)
        cpsizer.Add(self.prevention_clinical_panel, 1, wx.EXPAND, 0)
        self.clinical_container_panel.SetSizer(cpsizer)
        cpsizer.Fit(self.clinical_container_panel)
        self.clinical_pane_sizer.RecalcSizes()

    def doNewPatient(self, event):
        """
        Menu handler for adding new patients
        """
        global db
        self.panel_1.Disable()
        olvDialog = OLVDialog(None, db, PatientIdentification, OlvPatientIdentification, OlvPatientIdentificationCols)
        rc = olvDialog.ShowModal()
        self.panel_1.Enable()
        
    def doSelectPatient(self, event):
        """
        Menu handler for selecting a patient to record
        """
        global db
        self.panel_1.Disable()
        olvDialog = OLVDialog(None, db, PatientIdentification, OlvPatientIdentification, OlvPatientIdentificationCols,"Select-Only")
        rc = olvDialog.ShowModal()
        if rc == 0:
            self.currentPatient = olvDialog.getSelectedObject()
            self.patient_id = self.currentPatient.patient_id
            self.patient_name.SetValue(self.currentPatient.patient_name)
            self.director.SetPatientId(self.patient_id)
            self.preventionDatabaseWriter.setPatientId(self.patient_id)
            self.start_button.Enable()
            self.prevention_clinical_panel.setPatient(self.currentPatient.patient_id, self.currentPatient.patient_name)
            self.prevention_clinical_panel.showAllRecords()
        self.panel_1.Enable()

        
    def doStartRecording(self, event):  # wxGlade: MainFrame.<event_handler>
        """
        Button handler for starting the recording of a patient
        TBD
        """
        # print "doStartRecording event handler"
        # self.depth_canvas.post_redraw_event()
        global recording
        self.SendSizeEvent()
        self.session = PreventionSession()
        self.session.patient_id = self.patient_id
        self.session.start_time = datetime.today()
        self.session.end_time = self.session.start_time
        self.session.depth_video_file_directory = ""
        (rc,msg) = self.sessionController.add(self.session)
        if rc != 0:
            self.SetStatusText(msg)
            return
        self.stop_button.Enable()
        self.start_button.Disable()
        self.director.SetSessionId(self.session.id)
        self.preventionDatabaseWriter.setSessionId(self.session.id)
        self.preventionDatabaseWriter.setExperimentId(self.experiment_id)
        self.session.depth_video_file_directory = self.director.GetDepthFileDirectory()
        try:
            os.makedirs(self.session.depth_video_file_directory)            
        except OSError as exc: # Python >2.5
            if exc.errno == errno.EEXIST and os.path.isdir(self.session.depth_video_file_directory):
                pass
            else: 
                # raise
                msg = "Unable to access directory: " + str(self.session.depth_video_file_directory) + ". Please insure that the drive is attached and unlocked."
                rc = util.showMessageDialog(msg, "Drive unavailable")
                self.start_button.Enable()
                self.stop_button.Disable()
                (rc,msg) = self.sessionController.deleteRecord(self.session.id)
                if rc != 0:
                    self.SetStatusText(msg)
                return
        freespace = util.GetFreeSpaceGB(self.director.GetDepthFileDirectory())
        if freespace < int(self.system_config['PREVENTION_FILE_SIZE_GB']):
            msg = "Not enough space to record patient. Need " + str(self.system_config['PREVENTION_FILE_SIZE_GB']) + " GB but found " + str(freespace) + " GB."
            rc = util.showMessageDialog(msg, "Out of space")
            (rc,msg) = self.sessionController.deleteRecord(self.session.id)
            if rc != 0:
                self.SetStatusText(msg)
            return
        self.depth_canvas.proc_.set_database_writer(self.preventionDatabaseWriter)
        self.depth_canvas.proc_.start_recording(str(self.session.depth_video_file_directory))
        recording = True
        # patientTurningController = PatientTurningController(db, PatientTurning, OlvPatientTurning, OlvPatientTurningCols)
        # self.results = patientTurningController.getByPatientBySessionByExperiment(patientId, sessionId, experimentId)
        # self.olv.SetObjects(self.results)
        self.CreateUpdatingList()

    def CreateUpdatingList(self):
        self.olv = BatchedUpdate(self.olv, 10)
        self.timerThread = IntervalTimer(5, self.UpdateList)
        self.timerThread.start()
        
    def UpdateList(self):
        print "patientId=%d, sessionId=%d, experimentId=%d" % (self.patient_id, self.session.id, self.experiment_id)
        patientTurningController = PatientTurningController(db, PatientTurning, OlvPatientTurning, OlvPatientTurningCols)
        # self.results = patientTurningController.getByPatientBySessionByExperiment(self.patient_id, self.session.id, self.experiment_id)
        self.results = patientTurningController.getByPatientBySessionByExperiment(self.patient_id, 1, self.experiment_id)
        wx.CallAfter(self.olv.SetObjects,self.results)
        
    def DoStopRecording(self, event):  # wxGlade: MainFrame.<event_handler>
        """
        Button handler stopping recording
        """
        global recording
        if recording:
            recording = False
            self.session.end_time = datetime.today()
            (rc,msg) = self.sessionController.update(self.session)
            if rc != 0:
                self.SetStatusText(msg)
                return
            self.depth_canvas.proc_.stop_recording()
            self.stop_button.Disable()
            self.start_button.Enable()
        if self.timerThread:
            print "stopping thread"
            self.timerThread.stop()
        
    def OnExit(self, event):  # wxGlade: MainFrame.<event_handler>
        """
        Menu handler for exiting
        """
        evt = wx.PyCommandEvent(wx.EVT_BUTTON.typeId,self.stop_button.GetId())
        wx.PostEvent(self, evt)
        sys.exit()
        
    def DoAlgorithmList(self, event):  # wxGlade: MainFrame.<event_handler>
        """
        Menu handler for adding, modifying, deleting algorithms and algorithm defaults
        """
        global db
        self.panel_1.Disable()
        olvDialog = AlgorithmDialog(None, db)
        rc = olvDialog.ShowModal()
        olvDialog.Destroy()
        # self.RefreshTabs()
        self.panel_1.Enable()
        
    def DoExperimentList(self, event):  # wxGlade: MainFrame.<event_handler>
        """
        Menu handler for adding, modifying, deleting experiments and experiment configurations
        """
        global db
        self.panel_1.Disable()
        olvDialog = ExperimentDialog(None, db)
        rc = olvDialog.ShowModal()
        olvDialog.Destroy()
        self.panel_1.Enable()
        
    def DoConfigList(self, event):  # wxGlade: MainFrame.<event_handler>
        """
        Menu handler for adding, editing, deleting system configuration parameters
        """
        global db
        self.panel_1.Disable()
        olvDialog = OLVDialog(None, db, SystemConfiguration, OlvSystemConfiguration, OlvSystemConfigurationCols)
        rc = olvDialog.ShowModal()
        olvDialog.Destroy()
        self.panel_1.Enable()
        
    def DoChangePassword(self, event):  # wxGlade: MainFrame.<event_handler>
        """
        Menu handler for adding, editing, deleting system configuration parameters
        """
        global db
        self.panel_1.Disable()
        changePasswordDialog = ChangePasswordDialog(None)
        changePasswordDialog.SetDb(db)
        rc = changePasswordDialog.ShowModal()
        # print "rc=%d" % rc
        if rc == 1:
            self.SetStatusText("Password successfully changed")
        changePasswordDialog.Destroy()
        self.panel_1.Enable()
    def __init__(self, parent, db, algorithmId=-1, mode="Add-Update-Delete"):
        """
        Constructor which creates the modal dialog and its widgets, instantiates an
        ObjectlistView and populates it with the results from a query containing all
        database objects in a class.
        Arguments:
            parent - Parent window
            db - Database connection object
            algorithmId - algorithmId (-1 for all)
            mode - Dialog mode which can be either "Add-Update-Delete" or "Select"
        """
        self.algorithm_id = algorithmId
        self.db = db
        self.obj = Experiment
        self.objOlv = OlvExperiment
        self.objOlvCols = OlvExperimentCols()
        width = self.objOlvCols.getTotalColumnWidth()
        wx.Dialog.__init__(self, parent, size=wx.Size(width,500))
        self.controller = ExperimentController(db, self.obj, self.objOlv, self.objOlvCols)
        try:
            self.results = self.controller.getAllForOLView(self.algorithm_id)
        except:
            self.results = []
        
        font = wx.Font(12, wx.DEFAULT, wx.NORMAL, wx.BOLD) 
        lbl = wx.StaticText(self, label=self.obj.displayTableName)
        lbl.SetFont(font)

        mainSizer = wx.BoxSizer(wx.VERTICAL)
        searchSizer = wx.BoxSizer(wx.HORIZONTAL)
        btnSizer = wx.BoxSizer(wx.HORIZONTAL)
        font = wx.Font(10, wx.SWISS, wx.NORMAL, wx.BOLD) 
        
        # create the search related widgets
        searchByLbl = wx.StaticText(self, label="Search By:")
        searchByLbl.SetFont(font)
        searchSizer.Add(searchByLbl, 0, wx.ALL, 5)
        
        self.search = wx.SearchCtrl(self, style=wx.TE_PROCESS_ENTER)
        self.search.Bind(wx.EVT_TEXT_ENTER, self.onSearch)
        searchSizer.Add(self.search, 0, wx.ALL, 5)
        
        self.resultsOlv = ObjectListView(self, style=wx.LC_REPORT
                                                        |wx.SUNKEN_BORDER)
        self.resultsOlv.SetEmptyListMsg("No Records Found")
        self.setResultsOlv()
        
        # create the button row
        if mode == "Select-Only":
            selectRecordBtn = wx.Button(self, label="Select")
            selectRecordBtn.Bind(wx.EVT_BUTTON, self.onSelectRecord)
            btnSizer.Add(selectRecordBtn, 0, wx.ALL, 5)
        
        if mode == "Add-Update-Delete":
            addRecordBtn = wx.Button(self, label="Add")
            addRecordBtn.Bind(wx.EVT_BUTTON, self.onAddRecord)
            btnSizer.Add(addRecordBtn, 0, wx.ALL, 5)
        
            editRecordBtn = wx.Button(self, label="Edit")
            editRecordBtn.Bind(wx.EVT_BUTTON, self.onEditRecord)
            btnSizer.Add(editRecordBtn, 0, wx.ALL, 5)
        
            deleteRecordBtn = wx.Button(self, label="Delete")
            deleteRecordBtn.Bind(wx.EVT_BUTTON, self.onDelete)
            btnSizer.Add(deleteRecordBtn, 0, wx.ALL, 5)
        
        showAllBtn = wx.Button(self, label="Show All")
        showAllBtn.Bind(wx.EVT_BUTTON, self.onShowAllRecord)
        btnSizer.Add(showAllBtn, 0, wx.ALL, 5)
        
        configBtn = wx.Button(self, label="Configuration")
        configBtn.Bind(wx.EVT_BUTTON, self.onConfiguration)
        btnSizer.Add(configBtn, 0, wx.ALL, 5)
        
        mainSizer.Add(lbl, 0, wx.CENTER)
        mainSizer.Add(searchSizer)
        mainSizer.Add(self.resultsOlv, 1, wx.ALL|wx.EXPAND, 5)
        mainSizer.Add(btnSizer, 0, wx.CENTER)
        self.SetSizer(mainSizer)
class ExperimentDialog(wx.Dialog):
    """
    This class implements the generic select/add/update/delete dialog for a database object.
    It constructs the list of objects and places them in an ObjectListView widget.
    It then implements the button handlers for calling the add_modify_dialog to add or modify
    the object. Selection and deletion are handled in this dialog by calling the
    olv_dialog_controller controller.
    Methods:
        __init__(parent, db, obj, objOlv, objOlvCols, mode) - creates the widgets in the panel and performs initialization
        getSelectedObject() - Gets the selected object in the ObjectListView
        onAddRecord(event) - Button handler to add a record to the database
        onEditRecord(event) - Button handler to edit a record
        onDeleteRecord(event) - Button handler to delete a record
        onSearch(event) - Search field handler to search database based on the user's filter choice and keyword
        onSelectRecord(event) - Button handler to select a record
        onShowAllRecord(event) - Button handler to update the record list to show all of them
        setResultsOlv() - Sets the columns and objects in the ObjectListView
        showAllRecords() - Shows all records in the object list view control
    """

    #----------------------------------------------------------------------
    def __init__(self, parent, db, algorithmId=-1, mode="Add-Update-Delete"):
        """
        Constructor which creates the modal dialog and its widgets, instantiates an
        ObjectlistView and populates it with the results from a query containing all
        database objects in a class.
        Arguments:
            parent - Parent window
            db - Database connection object
            algorithmId - algorithmId (-1 for all)
            mode - Dialog mode which can be either "Add-Update-Delete" or "Select"
        """
        self.algorithm_id = algorithmId
        self.db = db
        self.obj = Experiment
        self.objOlv = OlvExperiment
        self.objOlvCols = OlvExperimentCols()
        width = self.objOlvCols.getTotalColumnWidth()
        wx.Dialog.__init__(self, parent, size=wx.Size(width,500))
        self.controller = ExperimentController(db, self.obj, self.objOlv, self.objOlvCols)
        try:
            self.results = self.controller.getAllForOLView(self.algorithm_id)
        except:
            self.results = []
        
        font = wx.Font(12, wx.DEFAULT, wx.NORMAL, wx.BOLD) 
        lbl = wx.StaticText(self, label=self.obj.displayTableName)
        lbl.SetFont(font)

        mainSizer = wx.BoxSizer(wx.VERTICAL)
        searchSizer = wx.BoxSizer(wx.HORIZONTAL)
        btnSizer = wx.BoxSizer(wx.HORIZONTAL)
        font = wx.Font(10, wx.SWISS, wx.NORMAL, wx.BOLD) 
        
        # create the search related widgets
        searchByLbl = wx.StaticText(self, label="Search By:")
        searchByLbl.SetFont(font)
        searchSizer.Add(searchByLbl, 0, wx.ALL, 5)
        
        self.search = wx.SearchCtrl(self, style=wx.TE_PROCESS_ENTER)
        self.search.Bind(wx.EVT_TEXT_ENTER, self.onSearch)
        searchSizer.Add(self.search, 0, wx.ALL, 5)
        
        self.resultsOlv = ObjectListView(self, style=wx.LC_REPORT
                                                        |wx.SUNKEN_BORDER)
        self.resultsOlv.SetEmptyListMsg("No Records Found")
        self.setResultsOlv()
        
        # create the button row
        if mode == "Select-Only":
            selectRecordBtn = wx.Button(self, label="Select")
            selectRecordBtn.Bind(wx.EVT_BUTTON, self.onSelectRecord)
            btnSizer.Add(selectRecordBtn, 0, wx.ALL, 5)
        
        if mode == "Add-Update-Delete":
            addRecordBtn = wx.Button(self, label="Add")
            addRecordBtn.Bind(wx.EVT_BUTTON, self.onAddRecord)
            btnSizer.Add(addRecordBtn, 0, wx.ALL, 5)
        
            editRecordBtn = wx.Button(self, label="Edit")
            editRecordBtn.Bind(wx.EVT_BUTTON, self.onEditRecord)
            btnSizer.Add(editRecordBtn, 0, wx.ALL, 5)
        
            deleteRecordBtn = wx.Button(self, label="Delete")
            deleteRecordBtn.Bind(wx.EVT_BUTTON, self.onDelete)
            btnSizer.Add(deleteRecordBtn, 0, wx.ALL, 5)
        
        showAllBtn = wx.Button(self, label="Show All")
        showAllBtn.Bind(wx.EVT_BUTTON, self.onShowAllRecord)
        btnSizer.Add(showAllBtn, 0, wx.ALL, 5)
        
        configBtn = wx.Button(self, label="Configuration")
        configBtn.Bind(wx.EVT_BUTTON, self.onConfiguration)
        btnSizer.Add(configBtn, 0, wx.ALL, 5)
        
        mainSizer.Add(lbl, 0, wx.CENTER)
        mainSizer.Add(searchSizer)
        mainSizer.Add(self.resultsOlv, 1, wx.ALL|wx.EXPAND, 5)
        mainSizer.Add(btnSizer, 0, wx.CENTER)
        self.SetSizer(mainSizer)
        
    #----------------------------------------------------------------------
    def getSelectedObject(self):
        """
        Gets the selected object in the ObjectListView
        """
        return self.selectedObject
    
    #----------------------------------------------------------------------
    def onAddRecord(self, event):
        """
        Button handler to add a record to the database
        """
        dlg = AddModifyExperimentDialog(self.controller, self.obj, self.db, title="Add", addRecord=True)
        rc = dlg.ShowModal()
        if rc == 0:
            self.showAllRecords()
        
    #----------------------------------------------------------------------
    def onEditRecord(self, event):
        """
        Button handler to edit a record
        """
        selectedRow = self.resultsOlv.GetSelectedObject()
        if selectedRow == None:
            util.showMessageDialog("No row selected!", "Error")
            return
        dlg = AddModifyExperimentDialog(self.controller, self.obj, self.db, row=selectedRow, title="Modify",
                                           addRecord=False)
        rc = dlg.ShowModal()
        if rc == 0:
            self.showAllRecords()
        
    #----------------------------------------------------------------------
    def onDelete(self, event):
        """
        Button handler to delete a record
        """
        selectedRow = self.resultsOlv.GetSelectedObject()
        if selectedRow == None:
            util.showMessageDialog("No row selected!", "Error")
            return
        (rc, msg) = self.controller.deleteRecord(selectedRow.getKey())
        # Check return code from above and put up appropriate message dialog
        if rc == 0:
            util.showMessageDialog("Record Deleted Successfully!", "Success!", wx.ICON_INFORMATION)
        else:
            util.showMessageDialog(msg, "Failure!", wx.ICON_INFORMATION)
        self.showAllRecords()
        
    #----------------------------------------------------------------------
    def onConfiguration(self, event):
        """
        Button handler to show configuration parameters
        """
        selectedRow = self.resultsOlv.GetSelectedObject()
        if selectedRow == None:
            util.showMessageDialog("No row selected!", "Error")
            return
        algorithmId = selectedRow.getKey()
        olvDialog = ExperimentConfigurationDialog(None, self.db, algorithmId)
        rc = olvDialog.ShowModal()
        olvDialog.Destroy()
        self.Enable()
        self.showAllRecords()
        
    #----------------------------------------------------------------------
    def onSearch(self, event):
        """
        Search field handler to search database based on the user's filter choice and keyword
        """
        keyword = self.search.GetValue()
        Filter.TextSearch(self.resultsOlv,columns=(), text=keyword)
        
    #----------------------------------------------------------------------
    def onSelectRecord(self, event):
        """
        Button handler to select a record
        """
        selectedRow = self.resultsOlv.GetSelectedObject()
        if selectedRow == None:
            util.showMessageDialog("No row selected!", "Error")
            return
        key = selectedRow.getKey()
        self.selectedObject = self.controller.getRecordByKey(key)
        self.EndModal(0)
        
    #----------------------------------------------------------------------
    def onShowAllRecord(self, event):
        """
        Button handler to update the record list to show all of them
        """
        self.showAllRecords()
        
    #----------------------------------------------------------------------
    def setResultsOlv(self):
        """
        Sets the columns and objects in the ObjectListView
        """
        cd = self.objOlvCols.getColumnDefinitions()
        # print len(cd)
        self.resultsOlv.SetColumns(self.objOlvCols.getColumnDefinitions())
        self.resultsOlv.SetObjects(self.results)
        
    #----------------------------------------------------------------------
    def showAllRecords(self):
        """
        Shows all records in the object list view control
        """
        self.results = self.controller.getAllForOLView(self.algorithm_id)
        self.setResultsOlv()