Exemplo n.º 1
0
def pyvol_window():
    """ """

    from pymol.Qt.utils import loadUi

    dialog = QtWidgets.QDialog()
    uifile = os.path.join(os.path.dirname(__file__), 'pyvol_gui.ui')
    form = loadUi(uifile, dialog)

    refresh_installation_status(form)

    form.close_button.clicked.connect(dialog.close)
    form.run_button.clicked.connect(lambda: run_gui_pyvol(form))

    form.browse_button.clicked.connect(lambda: browse_pocket_file(form))
    form.load_button.clicked.connect(lambda: run_gui_load(form))

    form.install_remote_button.clicked.connect(
        lambda: install_remote_pyvol(form))
    form.install_cache_button.clicked.connect(
        lambda: install_local_pyvol(form))

    form.check_updates_button.clicked.connect(
        lambda: refresh_installation_status(form, check_for_updates=True))
    form.update_button.clicked.connect(lambda: update_pyvol(form))

    form.msms_included_cbox.stateChanged.connect(
        lambda: toggle_included_msms(form))

    dialog.show()
Exemplo n.º 2
0
    def load_form(self, name, dialog=None):
        '''Load a form from pmg_qt/forms/{name}.py'''
        import importlib
        if dialog is None:
            dialog = QtWidgets.QDialog(self)
            widget = dialog
        elif dialog == 'floating':
            widget = QtWidgets.QWidget(self)
        else:
            widget = dialog

        try:
            m = importlib.import_module('.forms.' + name, 'pmg_qt')
        except ImportError as e:
            if pymol.Qt.DEBUG:
                print('load_form import failed (%s)' % (e, ))
            uifile = os.path.join(os.path.dirname(__file__), 'forms',
                                  '%s.ui' % name)
            form = pymol.Qt.utils.loadUi(uifile, widget)
        else:
            if hasattr(m, 'Ui_Form'):
                form = m.Ui_Form()
            else:
                form = m.Ui_Dialog()

            form.setupUi(widget)

        if dialog == 'floating':
            dialog = QtWidgets.QDockWidget(widget.windowTitle(), self)
            dialog.setFloating(True)
            dialog.setWidget(widget)
            dialog.resize(widget.size())

        form._dialog = dialog
        return form
Exemplo n.º 3
0
 def __init__(self):
     from pymol.Qt import QtWidgets
     dialog = QtWidgets.QDialog()
     self.setupUi(dialog)
     self.populate_ligand_select_list()
     dialog.accepted.connect(self.accept)
     dialog.exec_()
Exemplo n.º 4
0
def make_dialog():
    # entry point to PyMOL's API
    from pymol import cmd

    # pymol.Qt provides the PyQt5 interface, but may support PyQt4
    # and/or PySide as well
    from pymol.Qt import QtWidgets
    from pymol.Qt.utils import loadUi
    from pymol.Qt.utils import getSaveFileNameWithExt

    # create a new Window
    dialog = QtWidgets.QDialog()

    # populate the Window from our *.ui file which was created with the Qt Designer
    uifile = os.path.join(os.path.dirname(__file__), 'demowidget.ui')
    form = loadUi(uifile, dialog)

    # callback for the "Ray" button
    def run():
        # get form data
        height = form.input_height.value()
        width = form.input_width.value()
        dpi = form.input_dpi.value()
        filename = form.input_filename.text()
        units = form.input_units.currentText()

        # calculate dots per centimeter or inch
        if units == 'cm':
            dots_per_unit = dpi * 2.54
        else:
            dots_per_unit = dpi

        # convert image size to pixels
        width *= dots_per_unit
        height *= dots_per_unit

        # render the image
        if filename:
            cmd.png(filename, width, height, dpi=dpi, ray=1, quiet=0)
        else:
            cmd.ray(width, height, quiet=0)
            print('No filename selected, only rendering on display')

    # callback for the "Browse" button
    def browse_filename():
        filename = getSaveFileNameWithExt(dialog,
                                          'Save As...',
                                          filter='PNG File (*.png)')
        if filename:
            form.input_filename.setText(filename)

    # hook up button callbacks
    form.button_ray.clicked.connect(run)
    form.button_browse.clicked.connect(browse_filename)
    form.button_close.clicked.connect(dialog.close)

    return dialog
Exemplo n.º 5
0
def run_plugin_gui():
    '''
    Open our custom dialog
    '''
    global dialog

    if dialog is None:
        dialog = QtWidgets.QDialog()
        uifile = os.path.join(os.path.dirname(__file__), 'gui.ui')
        form = loadUi(uifile, dialog)
        Isosurface(form)
    dialog.show()
def create_dialog():
    dialog = QtWidgets.QDialog()
    dialog.setWindowTitle('AlignIt Pymol plugin')
    layout = QtWidgets.QVBoxLayout(dialog)
    alignit = AlignItPlugin()
    actions = {
        'Read pharmacophore...': lambda: alignit.readAlignIt(dialog),
    }

    for name, action in actions.items():
        btn = QtWidgets.QPushButton(name, dialog)
        btn.pressed.connect(action)
        layout.addWidget(btn)

    return dialog
Exemplo n.º 7
0
    def __init__(self):
        # create a new Window
        self.dialog = QtWidgets.QDialog()
        # populate the Window from our *.ui file which was created with the Qt Designer
        uifile = os.path.join(os.path.dirname(__file__), 'widgetMPbuilder.ui')
        self.form = loadUi(uifile, self.dialog)

        # open always on detergents
        self.changeForm("detergent")
        self.protName = None
        self.membName = None
        self.scafName = None
        self.dataName = None
        self.runNumber = 0
        # name of the model
        self.modelName = ""
        # prefix
        self.prefixName = ""
        # crysol int prediction
        self.prediction = ""
        # crysol fit
        self.fit = ""
        # result of the fit
        self.fitResult = {'chi2': -9999, 'Rg': -9999, 'eDens': -9999}
        # whether to build a membrane or use prebuilt one
        self.buildMemb = False
        # hook up button callbacks
        self.form.button_build.clicked.connect(self.run_build)
        self.form.button_refinement.clicked.connect(self.run_refinement)
        self.form.button_crysol_fit.clicked.connect(self.run_crysol_fit)  # single fit of assembly to data
        self.form.button_crysol_predict.clicked.connect(self.run_crysol_predict)  # predict theory
        # self.form.button_crysol_predict.clicked.connect(lambda: self.run_crysol_predict(modelName))

        self.form.btn_browse_prot.clicked.connect(self.browse_filename_prot)
        self.form.btn_browse_lip.clicked.connect(self.browse_filename_lip)
        self.form.btn_browse_scaffold.clicked.connect(self.browse_filename_scaffold)
        self.form.btn_browse_data.clicked.connect(self.browse_filename_data)

        self.form.button_close.clicked.connect(self.dialog.close)

        # change GUI depending upon the choice of assembly type
        self.form.input_type.currentIndexChanged.connect(self.change_assembly)
        # emptyAssembly = assemble complex without transmembrane protein component
        self.form.checkBox_emptyAssembly.toggled.connect(self.emptyAssembly)
        # preOriProt = pre-oriented protein
        self.form.checkBox_3.toggled.connect(self.preOriProt)
        self.form.checkBox_prebuild_bilayer.toggled.connect(self.preBuildBilayer)
Exemplo n.º 8
0
    def show_plugin_info_dialog(self, info):
        dialog = QtWidgets.QDialog(None)
        dialog.setWindowTitle('Plugin Information')
        layout = QtWidgets.QVBoxLayout()
        table = QtWidgets.QTableWidget(0, 2)
        table.verticalHeader().hide()
        table.horizontalHeader().hide()
        table.horizontalHeader().setStretchLastSection(True)
        layout.addWidget(table)
        dialog.setLayout(layout)

        def add_line(label, text):
            row = table.rowCount()
            table.insertRow(table.rowCount())
            table_item = QtWidgets.QTableWidgetItem(label)
            table_item.setFlags(table_item.flags() &
                 ~(Qt.ItemIsEditable))
            table.setItem(row, 0, table_item)
            table_item = QtWidgets.QTableWidgetItem(text)
            table_item.setFlags(table_item.flags() &
                 ~(Qt.ItemIsEditable))
            table.setItem(row, 1, table_item)

        add_line('Name', info.name)
        if not info.is_temporary:
            add_line('Python Module Name', info.mod_name)
            add_line('Filename', info.filename)

        metadata = info.get_metadata()
        for label, value in metadata.items():
            add_line(label, value)

        if not info.is_temporary:
            if info.loaded:
                add_line('commands', ', '.join(info.commands))
        docstring = info.get_docstring() or 'No documentation available.'

        browser = QtWidgets.QTextBrowser()
        browser.setPlainText(docstring)
        layout.addWidget(browser)

        table.resizeColumnsToContents()

        dialog.resize(600, dialog.height())
        dialog.exec_()
Exemplo n.º 9
0
def pyvol_window():
    """ """

    from pymol.Qt.utils import loadUi

    dialog = QtWidgets.QDialog()
    uifile = os.path.join(os.path.dirname(__file__), 'pyvol_gui.ui')
    form = loadUi(uifile, dialog)

    refresh_installation_status(form)

    form.close_button.clicked.connect(dialog.close)
    form.run_button.clicked.connect(lambda: run_gui_pyvol(form))

    form.browse_button.clicked.connect(lambda: browse_pocket_file(form))
    form.load_button.clicked.connect(lambda: run_gui_load(form))

    dialog.show()
Exemplo n.º 10
0
    def displayTextDialog(self, text):
        """
        Opens a generic text dialog and displays provided text.
        """
        if not self.text_dialog:
            self.text_dialog = QtWidgets.QDialog()
            layout = QtWidgets.QVBoxLayout()
            self.text_dialog.setLayout(layout)
            self.text_dialog.text_display = QtWidgets.QPlainTextEdit()
            self.text_dialog.text_display.setReadOnly(True)
            self.text_dialog.text_display.setStyleSheet(
                "font-family: monospace, courier")
            size = self.text_dialog.size()
            size.setWidth(DEFAULT_TEXT_DIALOG_WIDTH)
            self.text_dialog.resize(size)
            layout.addWidget(self.text_dialog.text_display)

        self.text_dialog.text_display.setPlainText(text)
        self.text_dialog.show()
        self.text_dialog.raise_()
Exemplo n.º 11
0
def run_gui_qt():
    from pymol.Qt import QtWidgets
    from pymol.Qt.utils import loadUi

    # create new Window
    dialog = QtWidgets.QDialog()

    uifile = os.path.join(os.path.dirname(__file__), 'form.ui')
    form = loadUi(uifile, dialog)

    def browse_file():
        form.filenames, extension_filter = QtWidgets.QFileDialog.getOpenFileNames(
            dialog, 'Open', filter='JSON file (*.json)')

        if form.filenames:
            form.input_filename.setText(str(form.filenames))
            form.input_state.setText('0')
            obj_name = os.path.basename(form.filenames[0]).rsplit('.', 1)[0]
            form.input_object.setText(obj_name)

    form.browse_button.clicked.connect(browse_file)
    form.close_button.clicked.connect(dialog.close)
    form.input_filename.setReadOnly(True)

    @form.load_button.clicked.connect
    def load_from_gui_qt():
        state = int(form.input_state.text())
        obj_name = form.input_object.text()

        for fn in form.filenames:
            load_json(fn, obj_name, state)
            if state:
                state += 1
        dialog.close()

    dialog.show()
Exemplo n.º 12
0
    def __init__(self, _pymol_running=False, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.uiIcon = os.path.join(package_directory, 'UI', 'icon.png')
        self.exampleDataPath = os.path.join(package_directory, 'examples')
        fretrajUI = os.path.join(package_directory, 'UI', 'fretraj.ui')
        self.settingsUI = os.path.join(package_directory, 'UI', 'settings.ui')
        self.textUI = os.path.join(package_directory, 'UI', 'textpad.ui')
        utils.loadUi(fretrajUI, self)
        self.setWindowTitle("FRETraj")
        self.setWindowIcon(utils.QtGui.QIcon(self.uiIcon))
        self._pymol_running = _pymol_running
        self.statusBar().showMessage("Ready", 2000)
        self.readTheDocsURL = None
        self.settingsWindow = QtWidgets.QDialog(self)
        utils.loadUi(self.settingsUI, self.settingsWindow)
        self.settingsWindow.setWindowTitle("FRETraj - Settings")
        self.textWindow = QtWidgets.QDialog(self)
        utils.loadUi(self.textUI, self.textWindow)

        # initialize labels dictionary with defaults from GUI
        self.struct = None
        self.av = {}
        self.traj = {}
        self.labels = {'Position': {}, 'Distance': {}}
        self.labelName = self.comboBox_labelName.currentText()
        self.labelName_default = self.comboBox_labelName.currentText()
        self.distanceName = self.comboBox_distanceName.currentText()
        self.distanceName_default = self.comboBox_distanceName.currentText()
        self.update_labelDict()
        self.labels_default = copy.deepcopy(self.labels)

        # set root path
        root_err = 'No root directory specified. FRETraj is not initialized.'
        self.settings = {
            'root_path': None,
            'browser': None,
            'local_docs': None
        }
        if os.path.isfile(
                '{}/.fretraj_settings.conf'.format(package_directory)):
            with open('{}/.fretraj_settings.conf'.format(package_directory),
                      'r') as f:
                self.settings = json.load(f)
                if os.path.isdir(self.settings['root_path']):
                    self.lineEdit_rootDirectory.setText(
                        self.settings['root_path'])
                    self.settingsWindow.lineEdit_rootDirectory.setText(
                        self.settings['root_path'])
                else:
                    self.settings['root_path'] = None
                    self.setRootDirectory()
                    if not self.settings['root_path']:
                        raise ValueError(root_err)
        else:
            self.setRootDirectory()
            if not self.settings['root_path']:
                raise ValueError(root_err)

        # examples
        n_examples = 0
        fileformat = '.pdb'
        self.exampleQAction = {}
        files = [
            f for f in os.listdir(self.exampleDataPath)
            if f.endswith(fileformat)
        ]
        for example in files:
            self.exampleQAction[example] = self.menuLoad_Example.addAction(
                example.replace(fileformat, ''))
            self.exampleQAction[example].triggered.connect(
                functools.partial(self.openExample,
                                  self.exampleQAction[example].text(),
                                  fileformat))
            n_examples += 1
        if n_examples > 0:
            self.menuLoad_Example.removeAction(self.example_placeholder)

        # activate / deactivate GUI elements
        self.dyeRadius_spinBox_OnOff()
        self.push_computeACV.setEnabled(False)
        self.doubleSpinBox_contourValue.setEnabled(False)
        self.doubleSpinBox_contourValue_CV.setEnabled(False)
        self.spinBox_bfactor.setEnabled(False)
        self.spinBox_gaussRes.setEnabled(False)
        self.checkBox_transparentAV.setEnabled(False)
        self.doubleSpinBox_gridBuffer.setEnabled(False)
        self.push_calculateFRET.setEnabled(False)
        self.spinBox_statePDB.setEnabled(False)
        self.spinBox_atomID.setEnabled(False)
        self.push_transfer.setEnabled(False)
        self.push_loadParameterFile.setEnabled(False)
        self.push_showText.setEnabled(False)
        self.push_clear.setEnabled(False)
        if not _LabelLib_found:
            self.checkBox_useLabelLib.setEnabled(False)
            self.checkBox_useLabelLib.setChecked(False)

        # signals
        self.push_computeACV.clicked.connect(self.computeACV)
        self.push_loadPDB.clicked.connect(self.loadPDB)
        self.comboBox_simType.activated.connect(self.dyeRadius_spinBox_OnOff)
        self.push_calculateFRET.clicked.connect(self.calculateFRET)
        self.push_deleteLabel.clicked.connect(self.deleteLabel)
        self.push_deleteFRETparam.clicked.connect(self.deleteFRETparam)
        self.push_loadParameterFile.clicked.connect(self.loadParameterFile)
        self.doubleSpinBox_contourValue.valueChanged.connect(
            self.pymol_update_isosurface)
        self.doubleSpinBox_contourValue_CV.valueChanged.connect(
            self.pymol_update_isosurface)
        self.spinBox_bfactor.valueChanged.connect(self.pymol_update_isosurface)
        self.spinBox_gaussRes.valueChanged.connect(
            self.pymol_update_isosurface)
        self.doubleSpinBox_gridBuffer.valueChanged.connect(
            self.pymol_update_isosurface)
        self.checkBox_transparentAV.toggled.connect(
            self.pymol_update_isosurface)
        self.lineEdit_labelName.returnPressed.connect(self.makeLabel)
        self.lineEdit_distanceName.returnPressed.connect(self.makeFRETparam)
        self.comboBox_labelName.currentIndexChanged.connect(
            self.update_comboBox)
        self.actionAbout_FRETraj.triggered.connect(self.openAbout)
        self.comboBox_donorName.currentIndexChanged.connect(self.define_DA)
        self.comboBox_acceptorName.currentIndexChanged.connect(self.define_DA)
        self.comboBox_distanceName.currentIndexChanged.connect(
            self.update_comboBox)
        self.spinBox_statePDB.valueChanged.connect(self.update_PDBstate)
        self.push_setRootDirectory.clicked.connect(self.setRootDirectory)
        self.push_clear.clicked.connect(self.clear_pymol)
        self.actionDocumentation.triggered.connect(self.openDocumentation)
        self.spinBox_atomID.valueChanged.connect(self.update_atom)
        self.push_transfer.clicked.connect(self.transferToLabel)
        self.push_deleteFRET.clicked.connect(self.deleteFRET)
        self.actionSettings.triggered.connect(self.openSettings)
        self.push_showText.clicked.connect(self.openPDBFile)
        self.settingsWindow.push_root.clicked.connect(self.setRootDirectory)
        self.settingsWindow.push_browser.clicked.connect(self.set_browser)
        self.settingsWindow.push_localdocs.clicked.connect(
            self.set_localdocsDir)
Exemplo n.º 13
0
def VolumePanelDialog(parent, *args, **kwargs):
    window = QtWidgets.QDialog(parent)
    _VolumePanel(window, window, *args, **kwargs)
    return window
Exemplo n.º 14
0
def dialog(_self=None):
    if _self is None:
        from pymol import cmd as _self

    from pymol.Qt import QtWidgets
    from pymol.Qt.utils import loadUi

    names = _self.get_object_list()

    if len(names) < 2:
        msg = "Need at least 2 molecular objects"
        QtWidgets.QMessageBox.warning(None, "Warning", msg)
        return

    dialog = QtWidgets.QDialog()
    uifile = os.path.join(os.path.dirname(__file__), 'align.ui')
    form = loadUi(uifile, dialog)

    form.input_mobile.addItems(names)
    form.input_target.addItems(names)

    def get_command(*args):
        method = form.input_method.currentText()
        mobile = form.input_mobile.currentText()
        target = form.input_target.currentText()

        if form.check_many.isChecked():
            command = 'extra_fit %s, %s, \\\n    method=%s' % (mobile, target,
                                                               method)
        elif method == 'cealign':
            command = 'cealign %s, %s' % (target, mobile)
        else:
            command = '%s %s, %s' % (method, mobile, target)

        if method != 'cealign':
            if not form.group_outlier.isChecked():
                command += (', \\\n    cycles=0')
            else:
                command += (', \\\n'
                            '    cycles=%d, \\\n'
                            '    cutoff=%.1f' % (
                                form.input_cycles.value(),
                                form.input_cutoff.value(),
                            ))
            if method == 'fit':
                command += ', \\\n    matchmaker=1'

        command += (
            ', \\\n'
            '    mobile_state=%d, \\\n'
            '    target_state=%d' %
            (form.input_mobile_state.value(), form.input_target_state.value()))

        aln_obj = form.input_object.text()
        if aln_obj:
            command += ', \\\n    object=' + aln_obj

        return command

    def update_output_command(*args):
        form.group_outlier.setEnabled(
            form.input_method.currentText() != 'cealign')
        form.output_command.setText(get_command())

    def update_output_command_many(*args):
        mobile = form.input_mobile.currentText()
        if form.check_many.isChecked():
            if mobile == names[1] and form.input_target.currentText(
            ) == names[0]:
                form.input_mobile.setEditText('*')
        elif mobile == '*':
            if form.input_target.currentText() != names[1]:
                form.input_mobile.setEditText(names[1])
            else:
                form.input_mobile.setEditText(names[0])

        form.output_command.setText(get_command())

    def run():
        _self.do(get_command())

    # hook up events
    form.group_outlier.toggled.connect(update_output_command)
    form.check_many.toggled.connect(update_output_command_many)
    form.input_method.currentIndexChanged.connect(update_output_command)
    form.input_mobile.editTextChanged.connect(update_output_command)
    form.input_target.editTextChanged.connect(update_output_command)
    form.input_mobile_state.valueChanged.connect(update_output_command)
    form.input_target_state.valueChanged.connect(update_output_command)
    form.input_cycles.valueChanged.connect(update_output_command)
    form.input_cutoff.valueChanged.connect(update_output_command)
    form.input_object.textChanged.connect(update_output_command)
    form.button_ok.clicked.connect(run)

    update_output_command()
    dialog.show()
Exemplo n.º 15
0
def create_dialog():

    dialog = QtWidgets.QDialog()
    dialog.setWindowTitle('Lighting Settings')

    sliders = [
        "Diffuse Reflection",
        ('ambient', 0, 1, None),
        ('reflect', -1, 1, None),
        "Direct Light from Front",
        ('direct (+reflect)', -1, 1, None),  # diffuse, coupled with "reflect"
        ('spec_direct', 0, 1, None),
        ('spec_direct_power', 0, 100, 1),
        "Free placeable directed Lights",
        ('light_count', 1, 8, 1),
        ('edit_light', 1, 7, 1),
        "Specular Reflection",
        ('spec_count', -1, 8, 1),
        # ('spec_power', -1, 200, 1), # deprecated since v1.5
        ('shininess', 0, 100, None),  # same as spec_power
        ('spec_reflect', -0.01, 1, None),
        ('specular', 0, 1, None),
        ('specular_intensity (=specular)', 0, 1, None),  # same as specular
        "Ambient Occlusion (Surface only)",
        ('ambient_occlusion_mode', 0, 2, 1),
        ('ambient_occlusion_scale', 1.0, 50., None),
        ('ambient_occlusion_smooth', 1, 20, 1),
        "Ray trace only",
        ('power', 1, 10, None),
        ('reflect_power', 1, 10, None),
    ]

    layout = QtWidgets.QVBoxLayout(dialog)

    button_layout = QtWidgets.QHBoxLayout()
    layout.addLayout(button_layout)
    layout.setContentsMargins(5, 0, 5, 0)
    button_layout.addWidget(
        QtWidgets.QLabel("<font color=red>Presets:</font>"))

    presets = [
        ("Default", preset_default),
        ("Metal", preset_metal),
        ("Plastic", preset_plastic),
        ("Rubber", preset_rubber),
        ("X-Ray", preset_xray),
    ]

    for name, fun in presets:
        btn = QtWidgets.QPushButton(name, dialog)
        btn.pressed.connect(fun)
        btn.setAutoDefault(False)
        button_layout.addWidget(btn)

    form_layout = QtWidgets.QFormLayout()
    form_layout.setContentsMargins(0, 0, 0, 0)
    form_layout.setVerticalSpacing(0)
    form_layout.setLabelAlignment(Qt.AlignLeft)
    layout.addLayout(form_layout)

    for i, item in enumerate(sliders, 1):
        if isinstance(item, str):
            label = QtWidgets.QLabel("<font color=blue>" + item + "</font>")
            form_layout.addRow(label)
            continue

        name, min, max, res = item
        if res is None:
            res = 0.01 if (max - min < 100) else 0.1

        line_edit = QtWidgets.QLineEdit(dialog)
        slider = SettingSlider(dialog,
                               name.split()[0], min, max, res, line_edit)

        h_layout = QtWidgets.QHBoxLayout()
        h_layout.addWidget(slider, 3)
        h_layout.addWidget(line_edit, 1)

        form_layout.addRow(name, h_layout)

    return dialog
Exemplo n.º 16
0
def run_gui():
    """Main PyViewDock dialog window"""

    docked = get_docked()

    # create a new Window
    dialog = QtWidgets.QDialog()

    # populate the Window from our *.ui file which was created with the Qt Designer
    uifile = os.path.join(os.path.dirname(os.path.realpath(__file__)),
                          'gui.ui')
    widget = loadUi(uifile, dialog)

    # hide question mark and add minimize button
    widget.setWindowFlags(widget.windowFlags()
                          ^ QtCore.Qt.WindowContextHelpButtonHint
                          | QtCore.Qt.WindowMinimizeButtonHint)

    ##  ERROR MESSAGE  ------------------------------------------------
    def error_msg(text, informative_text=None):
        msg = QtWidgets.QMessageBox()
        msg.setIcon(QtWidgets.QMessageBox.Critical)
        msg.setWindowTitle("PyViewDock")
        msg.setText(text)
        if informative_text:
            msg.setInformativeText(informative_text)
        msg.exec_()

    ##  MENUBAR  ------------------------------------------------------

    show_column = widget.menuColumns.addMenu('Show')
    hide_column = widget.menuColumns.addMenu('Hide')
    hide_all = widget.menuColumns.addAction('buttonHideAll')
    hide_all.setText("Hide All")

    ##  I/O FILES  ----------------------------------------------------

    def clear_all():
        """Clear all the docked entries"""
        docked.clear()
        draw_table()

    def browse_open():
        """Callback for the 'Open' button"""
        supported_formats = {
            'PDB Dock >4 (*.pdb)': load_dock4,
            'ChimeraX (*.chimerax)': load_chimerax,
            'pyDock (*.ene; *.eneRST)': load_pydock,
            'XYZ (*.xyz)': load_xyz,
            'All Files(*)': None
        }
        default_suffix_format = {
            'pdb': 'PDB Dock >4 (*.pdb)',
            'chimerax': 'ChimeraX (*.chimerax)',
            'ene': 'pyDock (*.ene; *.eneRST)',
            'enerst': 'pyDock (*.ene; *.eneRST)',
            'xyz': 'XYZ (*.xyz)'
        }
        # launch open file dialog from system
        filename, format_selected = QtWidgets.QFileDialog.getOpenFileName(
            parent=dialog,
            caption='Open file containing docked structures',
            directory=os.getcwd(),
            filter=";;".join(supported_formats.keys()))
        if not filename: return
        # guess format from suffix
        if format_selected == 'All Files(*)':
            suffix = os.path.basename(filename).rpartition('.')[-1].lower()
            if suffix in default_suffix_format:
                format_selected = default_suffix_format[suffix]
            else:
                # error message
                error_msg(f"Unsupported format file:  .{suffix}")
                return
        # load file with corresponding format' function
        supported_formats[format_selected](filename)
        draw_table()

    def browse_export_data():
        """Callback for the 'Export Data' button"""
        supported_formats = {
            'CSV (*.csv)': 'csv',
            'Text (*.txt)': 'txt',
            'All Files(*)': None
        }
        default_suffix_format = {'csv': 'CSV (*.csv)', 'txt': 'Text (*.txt)'}
        # launch open file dialog from system
        filename, format_selected = QtWidgets.QFileDialog.getSaveFileName(
            parent=dialog,
            caption='Save file containing docked data',
            directory=os.getcwd(),
            filter=";;".join(supported_formats.keys()))
        if not filename: return
        # guess format from suffix
        if format_selected == 'All Files(*)':
            suffix = os.path.basename(filename).rpartition('.')[-1].lower()
            # if not in supported_formats, fallback to csv
            format_selected = default_suffix_format.get(
                suffix, default_suffix_format['csv'])
        # save file with corresponding format' arguments
        export_docked_data(filename, supported_formats[format_selected])

    ##  TABLE  --------------------------------------------------------

    headers = docked.headers

    def draw_table(headers=headers):
        """Fill the whole table with data from docked entries"""
        widget.tableDocked.clear()
        widget.tableDocked.setSortingEnabled(False)
        n_internal_columns = 3
        # check if requested headers in remarks
        headers = [i for i in headers if i in docked.remarks]
        # number of rows and columns
        widget.tableDocked.setColumnCount(len(headers) + n_internal_columns)
        widget.tableDocked.setRowCount(docked.n_entries)
        # fill table
        widget.tableDocked.setHorizontalHeaderLabels([""] *
                                                     n_internal_columns +
                                                     headers)
        for row, entry in enumerate(docked.entries):
            # hidden internal columns [n_entry, 'object', 'state']
            widget.tableDocked.setItem(row, 0,
                                       QtWidgets.QTableWidgetItem(str(row)))
            widget.tableDocked.setItem(
                row, 1,
                QtWidgets.QTableWidgetItem(str(entry['internal']['object'])))
            widget.tableDocked.setItem(
                row, 2,
                QtWidgets.QTableWidgetItem(str(entry['internal']['state'])))
            # assign to table cell
            for column, remark in enumerate(headers):
                value = entry['remarks'][remark]
                item = QtWidgets.QTableWidgetItem()
                item.setData(QtCore.Qt.EditRole, value)
                widget.tableDocked.setItem(row, column + n_internal_columns,
                                           item)
                widget.tableDocked.item(row, column +
                                        n_internal_columns).setTextAlignment(
                                            QtCore.Qt.AlignCenter)
        widget.tableDocked.resizeColumnsToContents()
        widget.tableDocked.resizeRowsToContents()
        for i in range(n_internal_columns):
            widget.tableDocked.hideColumn(i)
        # update columns menubar
        show_column.clear()
        hide_column.clear()
        for i in sorted(docked.remarks - set(headers)):
            action = show_column.addAction(i)
            action.triggered.connect(lambda chk, i=i: show_header(i))
        for i in headers:
            action = hide_column.addAction(i)
            action.triggered.connect(lambda chk, i=i: hide_header(i))
        # show table
        widget.tableDocked.setSortingEnabled(True)
        widget.tableDocked.show()

    def show_header(header):
        """Add a column to headers"""
        headers.append(header)
        draw_table()

    def hide_header(header):
        """Remove a column from headers"""
        headers.remove(header)
        draw_table()

    def hide_header_all():
        """Remove all column headers"""
        headers.clear()
        draw_table()

    def display_selected():
        """Display entries corresponding to selected rows"""
        #TODO: multiple selection
        selected_row = widget.tableDocked.selectedItems()
        if selected_row:
            row_n = selected_row[0].row()
            object = widget.tableDocked.item(row_n, 1).text()
            state = widget.tableDocked.item(row_n, 2).text()
            cmd.set('state', state)
            cmd.disable(" ".join(docked.objects))
            cmd.enable(object)

    draw_table()

    ##  CALLBACKS  ----------------------------------------------------

    widget.buttonOpen.triggered.connect(browse_open)
    widget.buttonExportData.triggered.connect(browse_export_data)
    widget.buttonClearAll.triggered.connect(clear_all)
    hide_all.triggered.connect(hide_header_all)
    widget.tableDocked.itemSelectionChanged.connect(display_selected)

    dialog.show()
Exemplo n.º 17
0
def make_dialog():
    '''
    Function which initiates the dialog
    '''

    from pymol import cmd
    from pymol.Qt import QtWidgets, QtGui, QtCore  # note this gives the PyQt5 rather than PyQt4 interface
    from pymol.Qt.utils import loadUi
    from pymol.Qt.utils import getSaveFileNameWithExt

    import pymol.Qt
    Qt = QtCore.Qt

    #make a viewer object accessible by all functions
    viewer = BXlink_viewer()

    QFileDialog = QtWidgets.QFileDialog
    getOpenFileNames = QFileDialog.getOpenFileNames

    # create a new Window
    dialog = QtWidgets.QDialog()

    # populate the Window from our *.ui file which was created with the Qt Designer
    uifile = os.path.join(os.path.dirname(__file__), 'PyXlinkViewer.ui')
    form = loadUi(uifile, dialog)

    #-------------------------------------------------------------------

    def open_file():
        '''
        Callback for the open_xlink_file button
        '''

        # get a filename using open file diagog - not the filename can have any extension
        startdir = os.getcwd()

        open_fname = getOpenFileNames(dialog, 'Open file', startdir)[0]

        if open_fname:

            #need to convert list object returned by open file dialog to a string
            xlink_file = "".join(open_fname)

            # only deal with files in jwalk format for now
            xlink_file_type = 'jwalk'

            viewer.set_xlink_file(xlink_file)
            viewer.set_xlink_file_type(xlink_file_type)
            viewer.parse_xlink_file()
            viewer.calculate_distances()
            viewer.test_monos_in_obj()
            populate_xlink_table()
            change_num_sat_viol()

            viewer.display()

#-------------------------------------------------------------------

    def populate_xlink_table():
        '''
        Populates the table with xlinks and mono-links according to which are currently set to be displayed
        '''

        obs_xlinks = viewer.obs_xlinks
        obs_monos = viewer.obs_monos

        w = form.table_xlinks

        #remove data if already
        w.setRowCount(0)

        entries = []

        for xl in obs_xlinks:

            str_dist = '{0:3.1f}'.format(xl.distance)
            entry = [xl.chain1, xl.resid1, xl.chain2, xl.resid2, str_dist]

            bAdded_entry = False
            if xl.distance <= viewer.threshold and viewer.show_satisied == True:
                entries.append(entry)
                bAdded_entry = True

            if xl.distance > viewer.threshold and viewer.show_violated == True:
                entries.append(entry)
                bAdded_entry = True

            # check that inters should be shown
            if bAdded_entry and xl.chain1 != xl.chain2 and viewer.show_inter == False:
                entries.pop()

            if bAdded_entry and xl.chain1 == xl.chain2 and viewer.show_intra == False:
                entries.pop()

        #now add the monolinks to end of table
        for m in obs_monos:
            if viewer.show_mono == True:
                entry = [m.chain, m.resid, '-', '-', '-']
                entries.append(entry)

        if entries:
            w.setColumnCount(len(entries[0]))
            w.setRowCount(len(entries))

            for i, row in enumerate(entries):
                for j, col in enumerate(row):
                    item = QtWidgets.QTableWidgetItem(col)
                    w.setItem(i, j, item)
                    #align text in centre of cell
                    item.setTextAlignment(Qt.AlignCenter)

            # set the columns to be equal width and fit in the table
            header = w.horizontalHeader()
            for i in range(0, len(entries[0])):
                header.setSectionResizeMode(i, QtWidgets.QHeaderView.Stretch)

#-------------------------------------------------------------------

    def export():
        '''
        Callback function for 'Export' button. Opens save file dialog and saves current table in csv format.
        For each entry in the table two additional columns are outputted. One containing the current threshold
        value, and one 'Sat/Viol' for which 'S' or 'V' is outputted depending on whether the xlink is satisfied
        or violated, given the currently set threshold value
        '''

        filename = getSaveFileNameWithExt(dialog,
                                          'Save As...',
                                          filter='csv file (*.csv)')

        if filename:

            table = form.table_xlinks

            num_cols = table.columnCount()
            num_rows = table.rowCount()

            with open(filename, 'w') as f:

                for i in range(0, num_cols):

                    item = table.horizontalHeaderItem(i)
                    f.write(item.text() + ',')
                f.write('Threshold,Sat-Viol\n')

                for i in range(0, num_rows):
                    for j in range(0, num_cols):

                        item = table.item(i, j)
                        text = item.text()
                        f.write(text + ',')

                    #last item retrieved was the distance for this xlink or a dash if a mono-link entry so use this to test if satisfied
                    if text == '-':
                        f.write('-,-\n')
                    else:
                        f.write(str(viewer.threshold) + ',')

                        if float(text) <= viewer.threshold:
                            f.write('S\n')
                        else:
                            f.write('V\n')

#----------------------------------------------------------------------------------------------------

# callback functions for checkboxes

    def check_satisfied_click():
        viewer.set_show_satisfied(form.check_satisfied.isChecked())

        populate_xlink_table()
        viewer.update()

    def check_violated_click():
        viewer.set_show_violated(form.check_violated.isChecked())

        populate_xlink_table()
        viewer.update()

    def check_inter_click():
        viewer.set_show_inter(form.check_inter.isChecked())
        populate_xlink_table()
        viewer.update()
        change_num_sat_viol()

    def check_intra_click():
        viewer.set_show_intra(form.check_intra.isChecked())
        populate_xlink_table()
        viewer.update()
        change_num_sat_viol()

    def check_mono_click():
        viewer.set_show_mono(form.check_mono.isChecked())
        populate_xlink_table()
        viewer.update()

#---------------------------------------------------------------------------

# Call back functions for colour change buttons

    def change_satisfied_colour():
        color = QtWidgets.QColorDialog.getColor()

        form.frame_satisfied_colour.setStyleSheet(
            "QWidget { background-color: %s}" % color.name())

        rgb_list = [color.redF(), color.greenF(), color.blueF()]
        viewer.set_satisfied_colour(rgb_list)
        viewer.update()

    def change_violated_colour():
        color = QtWidgets.QColorDialog.getColor()

        form.frame_violated_colour.setStyleSheet(
            "QWidget { background-color: %s}" % color.name())

        rgb_list = [color.redF(), color.greenF(), color.blueF()]
        viewer.set_violated_colour(rgb_list)
        viewer.update()

    def change_mono_colour():
        color = QtWidgets.QColorDialog.getColor()

        form.frame_mono_colour.setStyleSheet(
            "QWidget { background-color: %s}" % color.name())

        rgb_list = [color.redF(), color.greenF(), color.blueF()]
        viewer.set_mono_colour(rgb_list)
        viewer.update()

#---------------------------------------------------------------------------

# call back functions for doublespin boxes

    def change_threshold():
        viewer.set_threshold(form.doublespin_threshold.value())
        change_num_sat_viol()
        populate_xlink_table()
        viewer.update()

    def change_width():
        viewer.set_radius(form.doublespin_width.value())
        viewer.update()

    def change_mono_size():

        viewer.set_mono_size(form.doublespin_mono_size.value())
        viewer.update()

#---------------------------------------------------------------------------

    def change_num_sat_viol():
        '''
        Changes the numbers of satisfied and violated xlinks in line-edit boxes. Called when either a change to threshold value is made,
        or the intra or inter checkboxes are clicked on
        '''

        num_sat = 0
        num_viol = 0

        for xl in viewer.obs_xlinks:

            # NB. check that both residues are in structure, if one is not, don't class as either sat or viol as not known
            if xl.distance <= viewer.threshold and xl.bRes1_in_obj == True and xl.bRes2_in_obj == True:

                #check that inter/intra are selected
                if viewer.show_inter == True and xl.chain1 != xl.chain2:
                    num_sat += 1

                if viewer.show_intra == True and xl.chain1 == xl.chain2:
                    num_sat += 1

            if xl.distance > viewer.threshold and xl.bRes1_in_obj == True and xl.bRes2_in_obj == True:

                #check that inter/intra are selected
                if viewer.show_inter == True and xl.chain1 != xl.chain2:
                    num_viol += 1

                if viewer.show_intra == True and xl.chain1 == xl.chain2:
                    num_viol += 1

        form.line_edit_satisfied.setText(str(num_sat))
        form.line_edit_violated.setText(str(num_viol))

        form.line_edit_satisfied.setAlignment(Qt.AlignCenter)
        form.line_edit_violated.setAlignment(Qt.AlignCenter)

#-------------------------------------------------------------------------

    def change_selected_object(item):
        '''
        This function is called when the user clicks on an object name in the objects listbox. It updates the BXlink_viewer
        object with the currently selected PyMOL object
        '''

        viewer.set_obj(item.text())

#-------------------------------------------------------------------------

# initialise the viewer threshold and mono-size values in doublespin boxes - these are set in QtDesigner

    viewer.set_threshold(form.doublespin_threshold.value())
    viewer.set_mono_size(form.doublespin_mono_size.value())

    # initialise the widgets
    form.check_satisfied.setChecked(True)
    form.check_violated.setChecked(True)
    form.check_inter.setChecked(True)
    form.check_intra.setChecked(True)

    # stop object list box from resizing when objects are added
    w = form.list_select_object
    w.setFixedSize(149, 50)

    # fill the listbox with the current objects
    objects = cmd.get_names()

    for i, obj in enumerate(objects):
        item = QtWidgets.QListWidgetItem(obj)

        form.list_select_object.addItem(item)

        if i == 0:  #select the first item in the QListWidget
            item.setSelected(True)
            viewer.set_obj(item.text())

    form.list_select_object.setFocus()

    #call a function of clicking listbox item to update selected PyMOL object stored by viewer class
    form.list_select_object.itemClicked.connect(change_selected_object)

    # initialise colours in for satisfied, violated, and mono-links
    form.frame_satisfied_colour.setStyleSheet(
        "QWidget { background-color: %s}" % '#0000FF')  # initialise to blue
    form.frame_violated_colour.setStyleSheet(
        "QWidget { background-color: %s}" % '#FF0000')  # initialise to red
    form.frame_mono_colour.setStyleSheet("QWidget { background-color: %s}" %
                                         '#FFFF00')  # initialise to yellow

    # hook up the button callbacks
    form.button_open_xlink_file.clicked.connect(open_file)
    form.button_close.clicked.connect(dialog.close)
    form.button_satisfied_colour.clicked.connect(change_satisfied_colour)
    form.button_violated_colour.clicked.connect(change_violated_colour)
    form.button_mono_colour.clicked.connect(change_mono_colour)
    form.button_export.clicked.connect(export)

    # hook up the check box callbacks
    form.check_satisfied.clicked.connect(check_satisfied_click)
    form.check_violated.clicked.connect(check_violated_click)
    form.check_inter.clicked.connect(check_inter_click)
    form.check_intra.clicked.connect(check_intra_click)
    form.check_mono.clicked.connect(check_mono_click)

    # hook up the check box callbacks
    form.doublespin_threshold.valueChanged.connect(change_threshold)
    form.doublespin_width.valueChanged.connect(change_width)
    form.doublespin_mono_size.valueChanged.connect(change_mono_size)

    return dialog
Exemplo n.º 18
0
def qtdialog():
    dialog = QtWidgets.QDialog()
    uifile = os.path.join(os.path.dirname(__file__), 'excelexporter.ui')
    form = pymolqtutils.loadUi(uifile, dialog)
    form._dialog = dialog

    # pre-fill form with likely data
    names = pymol.cmd.get_object_list()
    names += ['(' + n + ')' for n in pymol.cmd.get_names('public_selections')]
    form.input_sele.addItems(names)

    checkboxes = {
        'x': form.check_x,
        'y': form.check_y,
        'z': form.check_z,
    }

    prop_names = [
        'model', 'segi', 'chain', 'resi', 'resv', 'resn', 'name', 'alt', 'b',
        'q', 'elem', 'type', 'formal_charge', 'partial_charge', 'numeric_type',
        'text_type', 'stereo', 'ID', 'rank', 'index', 'vdw', 'ss', 'color',
        'reps', 'protons', 'state'
    ]

    # user properties
    p_set = set()
    pymol.cmd.iterate('all',
                      'p_set_update(p)',
                      space={'p_set_update': p_set.update})
    prop_names.extend('p.' + prop for prop in sorted(p_set))

    ncols = 3

    for i, prop in enumerate(prop_names):
        check = QtWidgets.QCheckBox(prop, form.groupBox)
        form.gridLayout.addWidget(check, i // ncols, i % ncols, 1, 1)
        checkboxes[prop] = check

    # add state properties to list
    prop_names.extend('xyz')

    for prop in ['chain', 'resi', 'resn', 'name']:
        checkboxes[prop].setChecked(True)

    @form.button_ok.clicked.connect
    def _(*args):
        props = [p for p in prop_names if checkboxes[p].isChecked()]
        sele = form.input_sele.currentText()
        statetext = form.input_state.checkedButton().text()

        if statetext.startswith('current'):
            state = -1
        elif statetext.startswith('all'):
            state = 0
        else:
            state = STATELESS
            props = [p for p in props if p not in ['x', 'y', 'z']]

        if not _check_xlwings():
            return

        with pymolqtutils.PopupOnException():
            dumpexcel(sele, props, state)

    form._dialog.show()
Exemplo n.º 19
0
def make_dialog():
    # entry point to PyMOL's API
    from pymol import cmd

    # pymol.Qt provides the PyQt5 interface, but may support PyQt4
    # and/or PySide as well
    from pymol.Qt import QtWidgets
    from pymol.Qt.utils import loadUi
    from PyQt5 import QtGui
    import os
    from pymol import cmd, stored
    import gzip
    import json
    import random
    import string
    from numpy import log
    import numpy as np
    import copy
    import collections
    # create a new Window
    dialog = QtWidgets.QDialog()
    QtWidgets.QApplication.setStyle(QtWidgets.QStyleFactory.create('Fusion'))
    # populate the Window from our *.ui file which was created with the Qt Designer
    uifile = os.path.join(os.path.dirname(__file__), 'gui_alfa3.ui')
    form = loadUi(uifile, dialog)

    # global variables
    Hs_files = []
    Proteines_files = []
    Hs_paths = []
    Proteines_paths = []
    Jsons_paths = []
    solvent = 'non'

    # load protein with hot spots and json file with reference values
    def browse_filename_hs_protein():
        # load protein
        protein_path = QFileDialog.getOpenFileName(form, "Open File",
                                                   "C:\\User\\",
                                                   'PDB File (*.pdb)')
        protein_path = protein_path[0]
        Proteines_paths.append(protein_path)
        protein_path = protein_path.replace(os.path.sep, "\\")
        # load hs file
        hs_path = QFileDialog.getOpenFileName(form, "Open File", "C:\\User\\",
                                              'MOL2 File (*.mol2)')
        hs_path = hs_path[0]
        Hs_paths.append(hs_path)
        hs_path = hs_path.replace(os.path.sep, "\\")
        # load json
        jsons_path = QFileDialog.getOpenFileName(form, "Open File",
                                                 "C:\\User\\",
                                                 'json File (*.json)')
        jsons_path = jsons_path[0]
        Jsons_paths.append(jsons_path)

        if hs_path:
            hs_name = os.path.basename(os.path.normpath(hs_path))
            hs_name = os.path.splitext(hs_name)[0]
            if hs_name != ' ':
                Hs_files.append(hs_name)
                form.browser_files1.setText('\n '.join(Hs_files))

            protein_name = os.path.basename(os.path.normpath(protein_path))
            protein_name = os.path.splitext(protein_name)[0]
            if protein_name != ' ':
                Proteines_files.append(protein_name)
                form.browser_files1_2.setText('\n '.join(Proteines_files))

    # load files that are browsed
    def load_hs_protein():
        if len(Hs_files) == len(Proteines_files):
            cmd.delete('all')
            for nbr in range(0, len(Hs_files)):
                cmd.load(Hs_paths[nbr])
                cmd.select(Hs_files[nbr])
                cmd.load(Proteines_paths[nbr])
                rezise(nbr)
            try:
                cmd.extra_fit(','.join(Hs_files))
                cmd.extra_fit(','.join(Proteines_files))
            except:
                form.browser_files1.setText('ERROR -_-')
                form.browser_files1_2.setText(
                    'Number of HotSpots and Structures must be the same!!!')

        else:
            form.browser_files1.setText('ERROR      -_-')
            form.browser_files1_2.setText(
                'Number of HotSpots and Structures must be the same!!!')

    # change size of hs depends on reference_density_correction from .json file (one fil for one pond calculations)
    def rezise(nbrs):
        def is_sele(sele):
            return sele in cmd.get_names('all')

        def _random_string(n=10):
            return ''.join(
                random.choice(string.ascii_uppercase + string.digits)
                for _ in range(n))

        refs = []
        ref = 1
        for i in range(0, len(Jsons_paths)):
            with gzip.open(Jsons_paths[i]) as f:
                refOne = float(json.load(f)["reference_density_correction"])
                refs.append(refOne)

        if form.oneSolvent.isChecked():
            ref = np.median(refs)
        if form.multipleSolvent.isChecked():
            with gzip.open(Jsons_paths[nbrs]) as f:
                ref = float(json.load(f)["reference_density_correction"])
        else:
            ref = np.median(refs)

        def hs_resize(meta_file, selection):

            if not is_sele(selection):
                raise RuntimeError(
                    "Selection \"{}\" does not exists.".format(selection))

            # Find free sele name
            temp_sele = _random_string()
            while is_sele(temp_sele):
                temp_sele = _random_string()

            states = cmd.count_states(selection=selection)

            for state in range(1, states + 1):
                stored.info = []
                cmd.iterate_state(state, selection,
                                  "stored.info.append((ID, partial_charge))")

                for id_, partial_charge in stored.info:
                    size = log(partial_charge / ref + 1)
                    print(ref)
                    print(size)

                    cmd.select(temp_sele,
                               "{} and id {}".format(selection, id_),
                               state=state)
                    cmd.set("sphere_scale", value=size, selection=temp_sele)
                    cmd.alter(temp_sele, "b={}".format(partial_charge))

            cmd.delete(temp_sele)

        hs_resize(Jsons_paths[nbrs], Hs_files[nbrs])

    # save all hs into one mol2 file
    def save_all_hs():
        cmd.select('sele', 'resn FIL')
        file_name = QFileDialog.getSaveFileName(form, 'Save File', '',
                                                'MOL2 File (*.mol2)')
        file_name = file_name[0]
        cmd.create('all_hs', 'sele')
        cmd.save(file_name, 'all_hs', 0)
        cmd.delete('all_hs')

    # simplification geometric centre / hs weights
    def hs_sipmly():

        cmd.delete('simply')

        def is_sele(sele):
            return sele in cmd.get_names("all")

        def find_all_coords(n, hs_id, exc_indexes=[], coords=[]):

            for node in n[hs_id]:
                if (node[0], node[3]) not in exc_indexes:
                    exc_indexes.append((node[0], node[3]))
                    coords.append(node[2])
                    find_all_coords(n, (node[0], node[3]),
                                    exc_indexes=exc_indexes,
                                    coords=coords)
            return exc_indexes, coords

        def free_hotspot_id(hs, exc_indexes):

            for h in hs:
                if (h[0], h[3]) not in exc_indexes:
                    return h[0], h[3]

            return None

        def group_center(coords):
            length = coords.shape[0]
            sum_x = np.sum(coords[:, 0])
            sum_y = np.sum(coords[:, 1])
            sum_z = np.sum(coords[:, 2])

            return sum_x / length, sum_y / length, sum_z / length

        def find_center(partial_charges, coords, nbr):
            dict_value_coords = {}
            coords_weight = []

            for p, c in zip(partial_charges, coords):
                dict_value_coords[p] = c
            od_dict = collections.OrderedDict(
                sorted(dict_value_coords.items(), reverse=True))
            partial_charges = list(od_dict.keys())
            nbr = len(partial_charges) - nbr

            for i in range(0, nbr):
                try:
                    max_hs = partial_charges[i]
                    x = od_dict[max_hs][0]
                    y = od_dict[max_hs][1]
                    z = od_dict[max_hs][2]
                    coords_weight.append([x, y, z])
                except:
                    pass
            return coords_weight

        def hs_gsimplifier(*args, **kwargs):

            radius = form.radius1.value()
            color = kwargs.get("color", "red")

            selections = args

            for selection in selections:
                if not is_sele(selection):
                    raise RuntimeError(
                        "Selection \"{}\" does not exists.".format(selection))

            states = cmd.count_states(selection=selections[0])
            hs_values = []
            all_coords = []
            for state in range(1, states + 1):
                stored.info = []

                for selection in selections:
                    cmd.iterate_state(
                        state, selection,
                        "stored.info.append([ID, partial_charge, (x,y,z), \"{}\"])"
                        .format(selection))
                for line in stored.info:
                    partial_charge = line[1]
                    coord = line[2]
                    hs_values.append(partial_charge)
                    all_coords.append(coord)

                hs = np.array(copy.copy(stored.info))

                n = dict()
                for h in hs:
                    dists = np.linalg.norm(np.array(h[2]) - list(zip(*hs))[2],
                                           axis=1)
                    # Convert to dict due to same hotspots IDs
                    n[(h[0], h[3])] = hs[dists <= radius]

                exc_indexes = []
                hs_id = free_hotspot_id(hs, exc_indexes=exc_indexes)

                while hs_id is not None:
                    excluded, coords = find_all_coords(n,
                                                       hs_id,
                                                       exc_indexes=[],
                                                       coords=[])
                    exc_indexes.extend(excluded)
                    if form.geometric.isChecked():
                        middle_point = group_center(np.array(coords))
                        cmd.pseudoatom(object="simply",
                                       color=color,
                                       pos=middle_point,
                                       state=state)
                    else:
                        middle_points = find_center(hs_values,
                                                    all_coords,
                                                    nbr=len(exc_indexes))
                        for point in middle_points:
                            cmd.pseudoatom(object="simply",
                                           color=color,
                                           pos=point,
                                           state=state)

                    hs_id = free_hotspot_id(hs, exc_indexes=exc_indexes)

                cmd.show(representation="spheres", selection="simply")

        cmd.select('hs2', 'resn FIL')
        hs_gsimplifier('hs2', color='hotpink')

    def save_simply():
        cmd.select('simply')
        file_name = QFileDialog.getSaveFileName(form, 'Save File', '',
                                                'MOL2 File (*.mol2)')
        file_name = file_name[0]
        cmd.save(file_name, 'simply')

    # make hs color
    def color_hs():
        color = form.colors.currentItem()
        color = str(color.text())

        try:
            cmd.spectrum("pc", ('%s' % color), 'sele')

        except:
            cmd.spectrum("pc", ('%s' % color), 'hotspot')
            cmd.spectrum("pc", '%s' % color, 'hs' + '*')

    def choose_hs(picked_hs=0):
        picked_hs = cmd.count_atoms('sele')
        form.hs_browse.setText(str(picked_hs))
        cmd.create('hs', 'sele')

    def clear_pick_hs():
        picked_hs = 0
        form.hs_browse.setText(str(picked_hs))

    def clean_all():
        cmd.delete('all')
        Hs_files.clear()
        Proteines_files.clear()
        Hs_paths.clear()
        Proteines_paths.clear()
        Jsons_paths.clear()
        form.browser_files1_2.setText(', '.join(Proteines_files))
        form.browser_files1.setText(', '.join(Proteines_files))
        form.hs_browse.setText(' ')

    def solvent_one():
        global solvent
        solvent = 'one'

    def solvent_multiple():
        global solvent
        solvent = 'multiple'

    def search_groups():
        radius2 = form.radius2.value()
        cmd.select('sele_atms', 'polymer.protein within %f of hs' % (radius2))

    def save_atms():
        cmd.select('sele_atms')
        file_name = QFileDialog.getSaveFileName(form, 'Save File', '',
                                                'PDB File (*.pdb)')
        file_name = file_name[0]
        cmd.save(file_name, 'sele_atms', -1)

    # hook up button callbacks
    form.browse_button1.clicked.connect(browse_filename_hs_protein)
    form.load1.clicked.connect(load_hs_protein)
    form.button_close.clicked.connect(dialog.close)
    form.save_file1.clicked.connect(save_all_hs)
    form.color_button.clicked.connect(color_hs)
    form.clear_all.clicked.connect(clean_all)
    form.clear_files1.clicked.connect(clean_all)
    form.ok1.clicked.connect(hs_sipmly)
    form.save_file2_2.clicked.connect(save_simply)
    form.add_hs.clicked.connect(choose_hs)
    form.clear_hs.clicked.connect(clear_pick_hs)
    form.oneSolvent.clicked.connect(solvent_one)
    form.multipleSolvent.clicked.connect(solvent_multiple)
    form.ok2.clicked.connect(search_groups)
    form.save_file3.clicked.connect(save_atms)
    return dialog
Exemplo n.º 20
0
def dialog(_self=None):
    if _self is None:
        from pymol import cmd as _self

    dialog = QtWidgets.QDialog()
    uifile = os.path.join(os.path.dirname(__file__), 'apbs.ui')
    form = loadUi(uifile, dialog)
    form._dialog = dialog
    form._proclist = []

    def set_apbs_in(contents):
        form.apbs_template.setPlainText(contents.strip())

    # hide options widgets
    form.optarea_prep.setVisible(False)
    form.optarea_apbs.setVisible(False)
    form.optarea_surf.setVisible(False)
    form.optarea_other.setVisible(False)

    # pre-fill form with likely data
    names = _self.get_object_list()
    names += ['(' + n + ')' for n in _self.get_names('public_selections')]
    if names:
        form.input_sele.clear()
        form.input_sele.addItems([
            ('polymer & ' +
             name) if _self.count_atoms('polymer & ' + name) > 0 else name
            for name in names
        ])
    form.surf_map.addItems(_self.get_names_of_type('object:map'))
    set_apbs_in(electrostatics.template_apbs_in)

    # executables
    from distutils.spawn import find_executable
    form.apbs_exe.setText(electrostatics.find_apbs_exe() or 'apbs')
    form.pdb2pqr_exe.setText(
        find_executable('pdb2pqr') or
        # acellera::htmd-pdb2pqr provides pdb2pqr_cli
        find_executable('pdb2pqr_cli') or find_executable(
            'share/pdb2pqr/pdb2pqr.py', os.getenv('FREEMOL', '/usr'))
        or 'pdb2pqr')

    # for async panels
    form._callInMainThread = MainThreadCaller()
    run_impl_async = AsyncFunc(run_impl)

    # "Run" button callback
    def run():
        form.tabWidget.setEnabled(False)
        form.button_ok.clicked.disconnect()
        form.button_ok.clicked.connect(abort)
        form.button_ok.setText('Abort')

        form._capture = StdOutCapture()

        # detach from main thread
        run_impl_async(form, _self)

    # "Run" button "finally" actions (main thread)
    @run_impl_async.finished.connect
    def run_finally(args):
        _, exception = args

        form._proclist[:] = []
        stdout = form._capture.release()
        print(stdout)

        form.button_ok.setText('Run')
        form.button_ok.clicked.disconnect()
        form.button_ok.clicked.connect(run)
        form.button_ok.setEnabled(True)
        form.tabWidget.setEnabled(True)

        if exception is not None:
            handle_exception(exception, stdout)
            return

        quit_msg = "Finished with Success. Close the APBS dialog?"
        if QMessageBox.Yes == QMessageBox.question(form._dialog, 'Finished',
                                                   quit_msg, QMessageBox.Yes,
                                                   QMessageBox.No):
            form._dialog.close()

    def handle_exception(e, stdout):
        if isinstance(e, SilentAbort):
            return

        msg = str(e) or 'unknown error'
        msgbox = QMessageBox(QMessageBox.Critical, 'Error', msg,
                             QMessageBox.Close, form._dialog)
        if stdout.strip():
            msgbox.setDetailedText(stdout)
        msgbox.exec_()

    # "Abort" button callback
    def abort():
        form.button_ok.setEnabled(False)
        while form._proclist:
            p = form._proclist.pop()
            try:
                p.terminate()
                p.returncode = -15  # SIGTERM
            except OSError as e:
                print(e)

    # selection checker
    check_sele_timer = QtCore.QTimer()
    check_sele_timer.setSingleShot(True)

    # grid auto-value
    form.apbs_grid_userchanged = False
    form.apbs_grid.setStyleSheet('background: #ff6')

    @form.apbs_grid.editingFinished.connect
    def _():
        form.apbs_grid_userchanged = True
        form.apbs_grid.setStyleSheet('')

    @check_sele_timer.timeout.connect
    def _():
        has_props = ['no', 'no']

        def callback(partial_charge, elec_radius):
            if partial_charge: has_props[0] = 'YES'
            if elec_radius > 0: has_props[1] = 'YES'

        n = _self.iterate(form.input_sele.currentText(),
                          'callback(partial_charge, elec_radius)',
                          space={'callback': callback})

        # grid auto-value (keep map size in the order of 200x200x200)
        if n > 1 and not form.apbs_grid_userchanged:
            e = _self.get_extent(form.input_sele.currentText())
            volume = (e[1][0] - e[0][0]) * (e[1][1] - e[0][1]) * (e[1][2] -
                                                                  e[0][2])
            grid = max(0.5, volume**0.333 / 200.0)
            form.apbs_grid.setValue(grid)

        if n < 1:
            label = 'Selection is invalid'
            color = '#f66'
        elif has_props == ['YES', 'YES']:
            label = 'No preparation necessary, selection has charges and radii'
            form.do_prepare.setChecked(False)
            color = '#6f6'
        else:
            label = 'Selection needs preparation (partial_charge: %s, elec_radius: %s)' % tuple(
                has_props)
            form.do_prepare.setChecked(True)
            color = '#fc6'

        form.label_sele_has.setText(label)
        form.label_sele_has.setStyleSheet('background: %s; padding: 5' % color)

    check_sele_timer.start(0)

    @form.apbs_exe_browse.clicked.connect
    def _():
        fnames = getOpenFileNames(None,
                                  filter='apbs (apbs*);;All Files (*)')[0]
        if fnames:
            form.apbs_exe.setText(fnames[0])

    @form.pdb2pqr_exe_browse.clicked.connect
    def _():
        fnames = getOpenFileNames(
            None, filter='pdb2pqr (pdb2pqr*);;All Files (*)')[0]
        if fnames:
            form.pdb2pqr_exe.setText(fnames[0])

    # hook up events
    form.input_sele.currentIndexChanged.connect(
        lambda: check_sele_timer.start(0))
    form.input_sele.editTextChanged.connect(
        lambda: check_sele_timer.start(1000))

    form.button_ok.clicked.connect(run)

    # "Register" opens a web browser
    @form.button_register.clicked.connect
    def _():
        import webbrowser
        webbrowser.open("http://www.poissonboltzmann.org/")

    @form.button_load.clicked.connect
    def _():
        fnames = getOpenFileNames(None,
                                  filter='APBS Input (*.in);;All Files (*)')[0]
        if fnames:
            contents = load_apbs_in(form, fnames[0])
            set_apbs_in(contents)

    @form.button_reset.clicked.connect
    def _():
        set_apbs_in(electrostatics.template_apbs_in)

    form._dialog.show()
    form._dialog.resize(500, 600)
Exemplo n.º 21
0
def dialog(_self=None):
    if _self is None:
        from pymol import cmd as _self

    from pymol.Qt import QtWidgets
    from pymol.Qt.utils import loadUi

    names = _self.get_object_list('enabled')

    if len(names) < 2 and _self.count_states('enabled') < 2:
        msg = "Need 2 molecular objects or one multistate object"
        QtWidgets.QMessageBox.warning(None, "Warning", msg)
        return

    dialog = QtWidgets.QDialog()
    uifile = os.path.join(os.path.dirname(__file__), 'morph.ui')
    form = loadUi(uifile, dialog)

    # pre-fill form with likely data
    form.input_sele1.addItems(names)
    form.input_sele2.addItems(names)
    if len(names) > 1:
        form.input_sele2.setEditText(names[1])
    else:
        form.input_state1.setValue(0)
    form.input_name.setText(_self.get_unused_name("morph"))

    def get_command(*args):
        morph = "linear"
        if form.input_method_rigimol.isChecked():
            morph = 'rigimol'

        sele1 = form.input_sele1.currentText()
        sele2 = form.input_sele2.currentText()

        try:
            nstates1 = _self.count_states(sele1)
            nstates2 = _self.count_states(sele2)

            form.input_state1.setMaximum(nstates1)
            form.input_state2.setMaximum(nstates2)
        except Exception as e:
            nstates1 = 1
            print(e)

        state1 = form.input_state1.value()
        state2 = form.input_state2.value()

        allstates = (state1 == 0 and nstates1 > 1)
        if allstates:
            sele2 = sele1
            state2 = 0

        form.input_sele2.setDisabled(allstates)
        form.input_state2.setDisabled(allstates)
        form.superpose.setDisabled(allstates)

        command = (
            'morph %s, %s, %s, %d, %d, %d, %d, %s' %
            (form.input_name.text(), sele1, sele2, state1, state2,
             form.input_refinement.value(), form.input_steps.value(), morph))

        if not allstates and form.superpose.isChecked():
            command = (('align %s, %s, '
                        'mobile_state=%d, target_state=%d\n' %
                        (form.input_sele1.currentText(),
                         form.input_sele2.currentText(), state1, state2)) +
                       command)

        return command

    def update_output_command(*args):
        form.output_command.setText(get_command())

    def run():
        _self.do(get_command())

    # hook up events
    form.input_sele1.editTextChanged.connect(update_output_command)
    form.input_sele2.editTextChanged.connect(update_output_command)
    form.input_state1.valueChanged.connect(update_output_command)
    form.input_state2.valueChanged.connect(update_output_command)
    form.superpose.stateChanged.connect(update_output_command)
    form.input_refinement.valueChanged.connect(update_output_command)
    form.input_steps.valueChanged.connect(update_output_command)
    form.input_method_rigimol.toggled.connect(update_output_command)
    form.input_method_linear.toggled.connect(update_output_command)
    form.input_name.textChanged.connect(update_output_command)
    form.button_ok.clicked.connect(run)

    update_output_command()
    dialog.show()
Exemplo n.º 22
0
def pyvol_window():
    """ """
    import os
    from pymol.Qt import QtCore, QtWidgets
    from pymol.Qt.utils import loadUi

    dialog = QtWidgets.QDialog()
    uifile = os.path.join(os.path.dirname(__file__), 'pyvolgui.ui')
    form = loadUi(uifile, dialog)

    def browse_pocket_file(form):
        """ Launches a window to select a file

        """
        pocket_file_name = QtWidgets.QFileDialog.getOpenFileNames(
            None,
            'Open file',
            os.getcwd(),
            filter='Pocket Files (*.obj *.csv)')[0][0]
        form.pocket_file_ledit.setText(pocket_file_name)

    def install_pyvol(form):
        """ Attempts a de novo PyVOL installation using pip

        """
        import distutils
        import subprocess
        import sys

        form.status_label.setText("Installing PyVOL and its dependencies")

        subprocess.check_output(
            [sys.executable, "-m", "pip", "install", "bio-pyvol"])

        msms_exe = distutils.spawn.find_executable("msms")
        if msms_exe == None:
            if os.name in ['posix']:
                conda_path = os.path.join(os.path.dirname(sys.executable),
                                          "conda")
                if not os.path.isfile(conda_path):
                    conda_path = "conda"
                subprocess.check_output(
                    [conda_path, "install", "-y", "-c", "bioconda", "msms"])
                msms_exe = distutils.spawn.find_executable("msms")
        try:
            from pymol import cmd
            from pyvol import pymol_interface
            cmd.extend('pocket', pymol_interface.pocket)
            cmd.extend('load_pocket', pymol_interface.load_pocket)
        except:
            pass
        refresh_installation_status(form)

    def uninstall_pyvol(form):
        """ Attempts to uninstall PyVOL using pip

        """
        import subprocess
        import sys

        form.status_label.setText("Uninstalling PyVOL")
        subprocess.check_output(
            [sys.executable, "-m", "pip", "uninstall", "-y", "bio-pyvol"])

        msg = QtWidgets.QMessageBox()
        msg.setIcon(QtWidgets.QMessageBox.Information)
        msg.setWindowTitle("PyVOL Backend Uninstalled")
        msg.setInformativeText(
            "The PyVOL backend has been uninstalled; however, the plugin must also be uninstalled using PyMOL's plugin manager."
        )
        msg.setStandardButtons(QtWidgets.QMessageBox.Ok)
        msg.setMinimumSize(QtCore.QSize(600, 200))  # Doesn't seem to work
        msg.exec_()

        refresh_installation_status(form)

    def update_pyvol(form):
        """ Attempts to update PyVOL using pip

        """
        import subprocess
        import sys

        form.status_label.setText("Updating PyVOL")
        subprocess.check_output(
            [sys.executable, "-m", "pip", "install", "--upgrade", "bio-pyvol"])

        msg = QtWidgets.QMessageBox()
        msg.setIcon(QtWidgets.QMessageBox.Information)
        msg.setWindowTitle("PyVOL Updated")
        msg.setInformativeText(
            "The PyVOL backend has been updated; however, PyMOL will not load the new code until it is restarted."
        )
        msg.setStandardButtons(QtWidgets.QMessageBox.Ok)
        msg.setMinimumSize(QtCore.QSize(600, 200))  # Doesn't seem to work
        msg.exec_()

        refresh_installation_status(form)

    def refresh_installation_status(form, check_for_updates=False):
        """ Check for updates and adjust the GUI to reflect the current installation status and availability of updates

        Args:
          check_for_updates (bool): query servers to see if an update is available? (Default value = False)

        """
        import distutils.spawn
        import json
        import subprocess
        import sys

        def apply_color(string, color):
            """ Applies a color to html text

            Args:
              string (str): text
              color (str): color to apply

            Returns:
              colored_text (str): html formatted text

            """
            return "<font color='{0}'>{1}</font>".format(color, string)

        all_pckgs = subprocess.check_output(
            [sys.executable, "-m", "pip", "list",
             "--format=json"]).decode('utf-8').strip()
        pckgs = json.loads(all_pckgs)

        pyvol_version = None
        biopython_version = None
        numpy_version = None
        pandas_version = None
        scipy_version = None
        sklearn_version = None
        trimesh_version = None

        pyvol_installed = False
        for pckg in pckgs:
            if pckg["name"] == "bio-pyvol":
                pyvol_version = pckg["version"]
                pyvol_installed = True

        for pckg in pckgs:
            if pckg["name"] == "biopython":
                biopython_version = pckg["version"]
                if pyvol_installed:
                    biopython_version = apply_color(biopython_version, "green")
            elif pckg["name"] == "numpy":
                numpy_version = pckg["version"]
                if pyvol_installed:
                    numpy_version = apply_color(numpy_version, "green")
            elif pckg["name"] == "pandas":
                pandas_version = pckg["version"]
                if pyvol_installed:
                    pandas_version = apply_color(pandas_version, "green")
            elif pckg["name"] == "scipy":
                scipy_version = pckg["version"]
                if pyvol_installed:
                    scipy_version = apply_color(scipy_version, "green")
            elif pckg["name"] == "scikit-learn":
                sklearn_version = pckg["version"]
                if pyvol_installed:
                    sklearn_version = apply_color(sklearn_version, "green")
            elif pckg["name"] == "trimesh":
                trimesh_version = pckg["version"]
                if pyvol_installed:
                    trimesh_version = apply_color(trimesh_version, "green")

        if pyvol_version is None:
            pyvol_version = apply_color("not found", "red")
        if biopython_version is None:
            biopython_version = apply_color("not found", "red")
        if numpy_version is None:
            numpy_version = apply_color("not found", "red")
        if pandas_version is None:
            pandas_version = apply_color("not found", "red")
        if scipy_version is None:
            scipy_version = apply_color("not found", "red")
        if sklearn_version is None:
            sklearn_version = apply_color("not found", "red")
        if trimesh_version is None:
            trimesh_version = apply_color("not found", "red")

        msms_exe = distutils.spawn.find_executable("msms")
        if msms_exe == None:
            msms_exe = apply_color("not found", "red")
        else:
            msms_exe = apply_color(msms_exe, "green")

        # check whether an update is available for PyVOL and modify the GUI appropriately
        update_available = False
        if pyvol_installed and (msms_exe is not None):
            form.run_tab.setEnabled(True)
            form.run_button.setEnabled(True)
            form.load_tab.setEnabled(True)
            form.uninstall_button.setEnabled(True)
            form.uninstall_button.clicked.connect(
                lambda: uninstall_pyvol(form))
            form.setWindowTitle("PyVOL v{0}".format(pyvol_version))

            if check_for_updates:
                avail_pckgs = subprocess.check_output([
                    sys.executable, "-m", "pip", "list", "--outdated",
                    "--format=json"
                ]).decode('utf-8').strip()
                avail = json.loads(avail_pckgs)
                for pckg in avail:
                    if pckg["name"] == "bio-pyvol":
                        update_available = True
                        pyvol_version = apply_color(
                            "{0} ({1} available)".format(
                                pyvol_version, pckg['latest_version']), "blue")
                        break

                if update_available:
                    form.status_label.setText("Update available")
                    form.install_button.setText("Update PyVOL")
                    form.install_button.clicked.connect(
                        lambda: update_pyvol(form))
                else:
                    form.status_label.setText("PyVOL is up-to-date")
                    pyvol_version = apply_color(
                        "{0} (up-to-date)".format(pyvol_version), "green")
                    form.install_button.setText("Check for Updates")
                    form.install_button.clicked.connect(
                        lambda: refresh_installation_status(
                            form, check_for_updates=True))
            else:
                form.install_button.setText("Check for Updates")
                form.status_label.setText("PyVOL is installed")
                form.install_button.clicked.connect(
                    lambda: refresh_installation_status(
                        form, check_for_updates=True))
        else:
            if not pyvol_installed:
                form.status_label.setText("PyVOL is not installed")
            else:
                form.status_label.setText(
                    "PyVOL has been installed but cannot run without MSMS")
            form.run_tab.setEnabled(False)
            form.run_button.setEnabled(False)
            form.load_tab.setEnabled(False)
            form.tabWidget.setCurrentIndex(2)
            form.install_button.setText("Install PyVOL")
            form.install_button.clicked.connect(lambda: install_pyvol(form))
            form.uninstall_button.setEnabled(False)

        gui_version = None
        if pyvol_installed and (not update_available):
            expected_gui_version = None
            try:
                import pyvol
                expected_gui_version = pyvol.__guiversion__
                if __version__ == expected_gui_version:
                    gui_version = apply_color(__version__, "green")
                else:
                    gui_version = apply_color(
                        "{0} ({1} expected)".format(__version__,
                                                    expected_gui_version),
                        "blue")
                    form.status_label.setText(
                        "GUI version mismatch--check whether PyVOL is up-to-date and reinstall the plugin if necessary using the PyMOL plugin manager or directly from the project <a href='https://github.com/schlessingerlab/pyvol/blob/master/pyvolgui.zip'>github</a>."
                    )
            except:
                gui_version = __version__
        else:
            gui_version = __version__

        form.install_status_browser.setText(
            ("&nbsp;   pyvol: {0}<br>"
             "&nbsp;   pyvol gui: {8}<br>"
             "&nbsp;   biopython: {1}<br>"
             "&nbsp;   numpy: {2}<br>"
             "&nbsp;   pandas: {3}<br>"
             "&nbsp;   scipy: {4}<br>"
             "&nbsp;   sklearn: {5}<br>"
             "&nbsp;   trimesh: {6}<br>"
             "&nbsp;   msms exe: {7}<br><br>").format(
                 pyvol_version, biopython_version, numpy_version,
                 pandas_version, scipy_version, sklearn_version,
                 trimesh_version, msms_exe, gui_version))

    def run_gui_load(form):
        """ Loads a precalculated pocket into PyMOL

        """
        from pyvol import pymol_interface

        # Loading Parameters
        pocket_file = form.pocket_file_ledit.text()
        if form.load_solid_rbutton.isChecked():
            display_mode = "solid"
        elif form.load_mesh_rbutton.isChecked():
            display_mode = "mesh"
        elif form.load_spheres_rbutton.isChecked():
            display_mode = "spheres"
        color = form.load_color_ledit.text()
        alpha = form.load_alpha_ledit.text()
        prefix = form.load_prefix_ledit.text()

        if color == "":
            color = None
        if alpha == "":
            alpha = None
        if prefix == "":
            prefix = None

        if not os.path.isfile(pocket_file):
            logger.error("Supplied file not found: {0}".format(pocket_file))
            return
        else:
            pymol_interface.load_pocket(pocket_file,
                                        name=prefix,
                                        display_mode=display_mode,
                                        color=color,
                                        alpha=alpha)

    def run_gui_pyvol(form):
        """ Runs a PyVOL calculation

        """
        from pyvol import pymol_interface

        # Basic Parameters
        protein = form.prot_sele_ledit.text()
        excl_org = form.excl_org_cbox.isChecked()
        min_rad = form.min_rad_ledit.text()
        max_rad = form.max_rad_ledit.text()
        constrain_inputs = form.constrain_cbox.isChecked()

        # Pocket Selection
        minimum_volume = None
        ligand = None
        lig_incl_rad = None
        lig_excl_rad = None
        residue = None
        resid = None
        pocket_coordinate = None

        if form.all_rbutton.isChecked():
            mode = "all"
            minimum_volume = form.min_volume_ledit.text()
        elif form.largest_rbutton.isChecked():
            mode = "largest"
        elif form.ligand_rbutton.isChecked():
            mode = "specific"
            ligand = form.lig_sele_ledit.text()
            if form.lig_incl_rad_ledit.text() != "":
                lig_incl_rad = form.lig_incl_rad_ledit.text()
            if form.lig_excl_rad_ledit.text() != "":
                lig_excl_rad = form.lig_excl_rad_ledit.text()
        elif form.residue_rbutton.isChecked():
            mode = "specific"
            residue = form.residue_sele_ledit.text()
        elif form.resid_rbutton.isChecked():
            mode = "specific"
            resid = form.resid_ledit.text()
        elif form.coordinate_rbutton.isChecked():
            mode = "specific"
            pocket_coordinate = form.coordinate_ledit.text()

        # Partitioning Parameters
        subdivide = form.subdivide_cbox.isChecked()
        if not subdivide:
            subdivide = None
        max_clusters = form.max_clusters_ledit.text()
        min_subpocket_rad = form.min_internal_rad_ledit.text()
        min_subpocket_surf_rad = form.min_surf_rad_ledit.text()

        # Display and Output Options
        if form.solid_rbutton.isChecked():
            display_mode = "solid"
        elif form.mesh_rbutton.isChecked():
            display_mode = "mesh"
        elif form.spheres_rbutton.isChecked():
            display_mode = "spheres"
        color = form.color_ledit.text()
        alpha = form.alpha_ledit.text()
        prefix = form.prefix_ledit.text()
        if prefix == "":
            prefix = None
        output_dir = form.output_dir_ledit.text()
        if output_dir == "":
            output_dir = None

        pymol_interface.pocket(protein=protein,
                               mode=mode,
                               ligand=ligand,
                               pocket_coordinate=pocket_coordinate,
                               residue=residue,
                               resid=resid,
                               prefix=prefix,
                               min_rad=min_rad,
                               max_rad=max_rad,
                               lig_excl_rad=lig_excl_rad,
                               lig_incl_rad=lig_incl_rad,
                               display_mode=display_mode,
                               color=color,
                               alpha=alpha,
                               output_dir=output_dir,
                               subdivide=subdivide,
                               minimum_volume=minimum_volume,
                               min_subpocket_rad=min_subpocket_rad,
                               min_subpocket_surf_rad=min_subpocket_surf_rad,
                               max_clusters=max_clusters,
                               excl_org=excl_org,
                               constrain_inputs=constrain_inputs)

    refresh_installation_status(form)

    form.close_button.clicked.connect(dialog.close)
    form.run_button.clicked.connect(lambda: run_gui_pyvol(form))

    form.browse_button.clicked.connect(lambda: browse_pocket_file(form))
    form.load_button.clicked.connect(lambda: run_gui_load(form))

    dialog.show()