def __init__(self, parent=None):
        super(SettingsMenu, self).__init__(parent)

        self.ui = Ui_SettingsMenu()
        self.ui.setupUi(self)
        self.setAttribute(QtCore.Qt.WA_DeleteOnClose)

        self.ui.buttonBox.clicked.connect(self.button_clicked)

        self.setup_prefs()
        self.setup_file_locs()
        self.setup_tags()
        self.setup_repl()
        self.setup_hacks()
 def __init__(self, parent = None):
   super(SettingsMenu, self).__init__(parent)
   
   self.ui = Ui_SettingsMenu()
   self.ui.setupUi(self)
   self.setAttribute(QtCore.Qt.WA_DeleteOnClose)
   
   self.ui.buttonBox.clicked.connect(self.button_clicked)
   
   self.setup_prefs()
   self.setup_file_locs()
   self.setup_tags()
   self.setup_repl()
   self.setup_hacks()
class SettingsMenu(QtGui.QDialog):
  def __init__(self, parent = None):
    super(SettingsMenu, self).__init__(parent)
    
    self.ui = Ui_SettingsMenu()
    self.ui.setupUi(self)
    self.setAttribute(QtCore.Qt.WA_DeleteOnClose)
    
    self.ui.buttonBox.clicked.connect(self.button_clicked)
    
    self.setup_prefs()
    self.setup_file_locs()
    self.setup_tags()
    self.setup_repl()
    self.setup_hacks()
  
################################################################################
### TAB: PREFERENCES
################################################################################
  def setup_prefs(self):
    for item in EDITOR_PREFS_CHK:
      self.ui.__dict__[item[CHK]].setChecked(common.editor_config.get_pref(item[CFG], item[DEFAULT]))
    
    for item in EDITOR_PREFS_TXT:
      self.ui.__dict__[item[TEXT]].setText(common.editor_config.get_pref(item[CFG]))
    
    # And our spellcheck language has to be handled manually.
    self.ui.cboSpellCheckLang.clear()
    self.ui.cboSpellCheckLang.addItems(enchant.list_languages())
    
    lang_index = self.ui.cboSpellCheckLang.findText(common.editor_config.spell_check_lang, Qt.Qt.MatchContains)
    self.ui.cboSpellCheckLang.setCurrentIndex(lang_index)
  
  def apply_prefs(self):
    for item in EDITOR_PREFS_TXT:
      if self.ui.__dict__[item[TEXT]].text().length() == 0:
        QtGui.QMessageBox.critical(self, "Error", "Please provide languages codes for both original and translated text.")
        return False
    
    # Then apply our changes.
    for item in EDITOR_PREFS_TXT:
      common.editor_config.set_pref(item[CFG], common.qt_to_unicode(self.ui.__dict__[item[TEXT]].text(), normalize = False))
        
    for item in EDITOR_PREFS_CHK:
      common.editor_config.set_pref(item[CFG], self.ui.__dict__[item[CHK]].isChecked())
    
    common.editor_config.spell_check_lang = self.ui.cboSpellCheckLang.currentText()
    
    return True

################################################################################
### TAB: FILE LOCATIONS
################################################################################
  # A helper function for our signal mapper.
  # Shows a dialog asking for a file or directory to use in the text box
  # associated with the given index.
  def __get_cfg_item(self, index):
    box     = FILE_LOCATIONS[index][TEXT]
    fn      = FILE_LOCATIONS[index][FN]
    filter  = FILE_LOCATIONS[index][FILTER]
    
    if filter:
      item = fn(self, self.ui.__dict__[box].text(), filter)
    else:
      item = fn(self, self.ui.__dict__[box].text())
    
    if not item == "":
      self.ui.__dict__[box].setText(item)
  
  def setup_file_locs(self):
    
    # Because the default margins are ugly as h*ck.
    self.ui.tabLocs.layout().setContentsMargins(0, 0, 0, 0)
    
    # Map our buttons to functions that retrieve the necessary data.
    cfg_mapper = QSignalMapper(self)
    
    for i, item in enumerate(FILE_LOCATIONS):
      self.connect(self.ui.__dict__[item[BTN]], QtCore.SIGNAL("clicked()"), cfg_mapper, QtCore.SLOT("map()"))
      cfg_mapper.setMapping(self.ui.__dict__[item[BTN]], i)
    
    self.connect(cfg_mapper, QtCore.SIGNAL("mapped(int)"), self.__get_cfg_item)
    
    # Load in all our info from the config file.
    for item in FILE_LOCATIONS:
      self.ui.__dict__[item[TEXT]].setText(common.editor_config.get_pref(item[CFG]))
  
  def apply_file_locs(self):
    # Check to make sure none of our boxes are blank.
    for item in FILE_LOCATIONS:
      if self.ui.__dict__[item[TEXT]].text().length() == 0:
        QtGui.QMessageBox.critical(self, "Error", "Please supply locations for all the listed files or folders.")
        return False
    
    # Then apply our changes.
    for item in FILE_LOCATIONS:
      common.editor_config.set_pref(item[CFG], common.qt_to_unicode(self.ui.__dict__[item[TEXT]].text(), normalize = False))
    
    return True
  
################################################################################
### TAB: TAGS
################################################################################
  def setup_tags(self):
    self.ui.treeTags.clear()
    self.ui.treeTags.header().setResizeMode(QtGui.QHeaderView.Stretch)
    self.ui.tabTags.setEnabled(False)
  
  def apply_tags(self):
    return True
  
  def add_tag(self):
    pass
    
  def del_tag(self):
    pass
    
  def move_tag_up(self):
    pass
    
  def move_tag_down(self):
    pass
    
  def move_tag_top(self):
    pass
    
  def move_tag_bottom(self):
    pass
  
################################################################################
### TAB: TEXT REPLACEMENT
################################################################################
  def setup_repl(self):
    self.ui.treeTextRepl.clear()
    self.ui.treeTextRepl.header().setResizeMode(QtGui.QHeaderView.Stretch)
    self.ui.tabRepl.setEnabled(True)
    
    for src, dst in common.editor_config.repl:
      self.add_repl(src, dst)
  
  def apply_repl(self):
    common.editor_config.repl = []
    
    for i in range(self.ui.treeTextRepl.topLevelItemCount()):
      item = self.ui.treeTextRepl.topLevelItem(i)
      src  = common.qt_to_unicode(item.text(0), normalize = False)
      dst  = common.qt_to_unicode(item.text(1), normalize = False)
      
      common.editor_config.repl.append((src, dst))
      
    return True
  
  def add_repl(self, src = u"???", dst = u"???"):
    new_sub = QtGui.QTreeWidgetItem([src, dst])
    new_sub.setFlags(new_sub.flags() | Qt.Qt.ItemIsEditable)
    self.ui.treeTextRepl.addTopLevelItem(new_sub)
  
  def del_repl(self):
    rows = self.ui.treeTextRepl.selectionModel().selectedRows()
    
    for row in rows:
      self.ui.treeTextRepl.takeTopLevelItem(row.row())
  
################################################################################
### TAB: HACKS
################################################################################
  def setup_hacks(self):
    self.ui.btnReloadHacks.clicked.connect(self.load_hacks)
    self.load_hacks()
  
  def load_hacks(self):
    reload(eboot_patch)
    
    self.ui.lstHacks.clear()
    
    for i, hack in enumerate(eboot_patch.EBOOT_PATCHES):
      name   = hack[eboot_patch.NAME]
      cfg_id = hack[eboot_patch.CFG_ID]
      
      if cfg_id and cfg_id in common.editor_config.hacks:
        enabled = common.editor_config.hacks[cfg_id]
      else:
        enabled = hack[eboot_patch.ENABLED]
      
      self.ui.lstHacks.addItem(name)
      self.ui.lstHacks.item(i).setCheckState(Qt.Qt.Checked if enabled else Qt.Qt.Unchecked)
      
      if cfg_id:
        self.ui.lstHacks.item(i).setData(Qt.Qt.UserRole, cfg_id)
        self.ui.lstHacks.item(i).setFlags(self.ui.lstHacks.item(i).flags() | Qt.Qt.ItemIsEnabled)
      else:
        self.ui.lstHacks.item(i).setData(Qt.Qt.UserRole, "")
        self.ui.lstHacks.item(i).setFlags(self.ui.lstHacks.item(i).flags() & ~Qt.Qt.ItemIsEnabled)
    
    self.ui.cboHackLang.clear()
    
    for lang in eboot_patch.LANGUAGES:
      self.ui.cboHackLang.addItem(lang)
    
    if eboot_patch.LANG_CFG_ID in common.editor_config.hacks:
      sys_lang = common.editor_config.hacks[eboot_patch.LANG_CFG_ID]
      self.ui.cboHackLang.setCurrentIndex(sys_lang)
    else:
      self.ui.cboHackLang.setCurrentIndex(0)
  
  def apply_hacks(self):
    for i in range(self.ui.lstHacks.count()):
      cfg_id  = common.qt_to_unicode(self.ui.lstHacks.item(i).data(Qt.Qt.UserRole).toString())
      enabled = self.ui.lstHacks.item(i).checkState() == Qt.Qt.Checked
      
      if cfg_id:
        common.editor_config.hacks[cfg_id] = enabled
    
    common.editor_config.hacks[eboot_patch.LANG_CFG_ID] = self.ui.cboHackLang.currentIndex()
      
    return True
  
################################################################################
### SLOTS
################################################################################
  def button_clicked(self, button):
    if self.ui.buttonBox.buttonRole(button) == QtGui.QDialogButtonBox.ApplyRole:
      self.apply_settings()
    
  def apply_settings(self):
    if self.apply_prefs() and self.apply_file_locs() and self.apply_tags() and \
       self.apply_repl() and self.apply_hacks():
      
      common.editor_config.save_config()
      return True
    else:
      return False
  
  ##############################################################################
  ### @fn   accept()
  ### @desc Overrides the Save button.
  ##############################################################################
  def accept(self):
    if self.apply_settings() == False:
      return
    
    super(SettingsMenu, self).accept()
  
  ##############################################################################
  ### @fn   reject()
  ### @desc Overrides the Cancel button.
  ##############################################################################
  def reject(self):
    super(SettingsMenu, self).reject()
class SettingsMenu(QtGui.QDialog):
    def __init__(self, parent=None):
        super(SettingsMenu, self).__init__(parent)

        self.ui = Ui_SettingsMenu()
        self.ui.setupUi(self)
        self.setAttribute(QtCore.Qt.WA_DeleteOnClose)

        self.ui.buttonBox.clicked.connect(self.button_clicked)

        self.setup_prefs()
        self.setup_file_locs()
        self.setup_tags()
        self.setup_repl()
        self.setup_hacks()

################################################################################
### TAB: PREFERENCES
################################################################################

    def setup_prefs(self):
        for item in EDITOR_PREFS_CHK:
            self.ui.__dict__[item[CHK]].setChecked(
                common.editor_config.get_pref(item[CFG], item[DEFAULT]))

        for item in EDITOR_PREFS_TXT:
            self.ui.__dict__[item[TEXT]].setText(
                common.editor_config.get_pref(item[CFG]))

        # And our spellcheck language has to be handled manually.
        self.ui.cboSpellCheckLang.clear()
        self.ui.cboSpellCheckLang.addItems(enchant.list_languages())

        lang_index = self.ui.cboSpellCheckLang.findText(
            common.editor_config.spell_check_lang, Qt.Qt.MatchContains)
        self.ui.cboSpellCheckLang.setCurrentIndex(lang_index)

    def apply_prefs(self):
        for item in EDITOR_PREFS_TXT:
            if self.ui.__dict__[item[TEXT]].text().length() == 0:
                QtGui.QMessageBox.critical(
                    self, "Error",
                    "Please provide languages codes for both original and translated text."
                )
                return False

        # Then apply our changes.
        for item in EDITOR_PREFS_TXT:
            common.editor_config.set_pref(
                item[CFG],
                common.qt_to_unicode(self.ui.__dict__[item[TEXT]].text(),
                                     normalize=False))

        for item in EDITOR_PREFS_CHK:
            common.editor_config.set_pref(
                item[CFG], self.ui.__dict__[item[CHK]].isChecked())

        common.editor_config.spell_check_lang = self.ui.cboSpellCheckLang.currentText(
        )

        return True

################################################################################
### TAB: FILE LOCATIONS
################################################################################
# A helper function for our signal mapper.
# Shows a dialog asking for a file or directory to use in the text box
# associated with the given index.

    def __get_cfg_item(self, index):
        box = FILE_LOCATIONS[index][TEXT]
        fn = FILE_LOCATIONS[index][FN]
        filter = FILE_LOCATIONS[index][FILTER]

        if filter:
            item = fn(self, self.ui.__dict__[box].text(), filter)
        else:
            item = fn(self, self.ui.__dict__[box].text())

        if not item == "":
            self.ui.__dict__[box].setText(item)

    def setup_file_locs(self):

        # Because the default margins are ugly as h*ck.
        self.ui.tabLocs.layout().setContentsMargins(0, 0, 0, 0)

        # Map our buttons to functions that retrieve the necessary data.
        cfg_mapper = QSignalMapper(self)

        for i, item in enumerate(FILE_LOCATIONS):
            self.connect(self.ui.__dict__[item[BTN]],
                         QtCore.SIGNAL("clicked()"), cfg_mapper,
                         QtCore.SLOT("map()"))
            cfg_mapper.setMapping(self.ui.__dict__[item[BTN]], i)

        self.connect(cfg_mapper, QtCore.SIGNAL("mapped(int)"),
                     self.__get_cfg_item)

        # Load in all our info from the config file.
        for item in FILE_LOCATIONS:
            self.ui.__dict__[item[TEXT]].setText(
                common.editor_config.get_pref(item[CFG]))

    def apply_file_locs(self):
        # Check to make sure none of our boxes are blank.
        for item in FILE_LOCATIONS:
            if self.ui.__dict__[item[TEXT]].text().length() == 0:
                QtGui.QMessageBox.critical(
                    self, "Error",
                    "Please supply locations for all the listed files or folders."
                )
                return False

        # Then apply our changes.
        for item in FILE_LOCATIONS:
            common.editor_config.set_pref(
                item[CFG],
                common.qt_to_unicode(self.ui.__dict__[item[TEXT]].text(),
                                     normalize=False))

        return True

################################################################################
### TAB: TAGS
################################################################################

    def setup_tags(self):
        self.ui.treeTags.clear()
        self.ui.treeTags.header().setResizeMode(QtGui.QHeaderView.Stretch)
        self.ui.tabTags.setEnabled(False)

    def apply_tags(self):
        return True

    def add_tag(self):
        pass

    def del_tag(self):
        pass

    def move_tag_up(self):
        pass

    def move_tag_down(self):
        pass

    def move_tag_top(self):
        pass

    def move_tag_bottom(self):
        pass

################################################################################
### TAB: TEXT REPLACEMENT
################################################################################

    def setup_repl(self):
        self.ui.treeTextRepl.clear()
        self.ui.treeTextRepl.header().setResizeMode(QtGui.QHeaderView.Stretch)
        self.ui.tabRepl.setEnabled(True)

        for src, dst in common.editor_config.repl:
            self.add_repl(src, dst)

    def apply_repl(self):
        common.editor_config.repl = []

        for i in range(self.ui.treeTextRepl.topLevelItemCount()):
            item = self.ui.treeTextRepl.topLevelItem(i)
            src = common.qt_to_unicode(item.text(0), normalize=False)
            dst = common.qt_to_unicode(item.text(1), normalize=False)

            common.editor_config.repl.append((src, dst))

        return True

    def add_repl(self, src=u"???", dst=u"???"):
        new_sub = QtGui.QTreeWidgetItem([src, dst])
        new_sub.setFlags(new_sub.flags() | Qt.Qt.ItemIsEditable)
        self.ui.treeTextRepl.addTopLevelItem(new_sub)

    def del_repl(self):
        rows = self.ui.treeTextRepl.selectionModel().selectedRows()

        for row in rows:
            self.ui.treeTextRepl.takeTopLevelItem(row.row())

################################################################################
### TAB: HACKS
################################################################################

    def setup_hacks(self):
        self.ui.btnReloadHacks.clicked.connect(self.load_hacks)
        self.load_hacks()

    def load_hacks(self):
        reload(eboot_patch)

        self.ui.lstHacks.clear()

        for i, hack in enumerate(eboot_patch.EBOOT_PATCHES):
            name = hack[eboot_patch.NAME]
            cfg_id = hack[eboot_patch.CFG_ID]

            if cfg_id and cfg_id in common.editor_config.hacks:
                enabled = common.editor_config.hacks[cfg_id]
            else:
                enabled = hack[eboot_patch.ENABLED]

            self.ui.lstHacks.addItem(name)
            self.ui.lstHacks.item(i).setCheckState(
                Qt.Qt.Checked if enabled else Qt.Qt.Unchecked)

            if cfg_id:
                self.ui.lstHacks.item(i).setData(Qt.Qt.UserRole, cfg_id)
                self.ui.lstHacks.item(i).setFlags(
                    self.ui.lstHacks.item(i).flags() | Qt.Qt.ItemIsEnabled)
            else:
                self.ui.lstHacks.item(i).setData(Qt.Qt.UserRole, "")
                self.ui.lstHacks.item(i).setFlags(
                    self.ui.lstHacks.item(i).flags() & ~Qt.Qt.ItemIsEnabled)

        self.ui.cboHackLang.clear()

        for lang in eboot_patch.LANGUAGES:
            self.ui.cboHackLang.addItem(lang)

        if eboot_patch.LANG_CFG_ID in common.editor_config.hacks:
            sys_lang = common.editor_config.hacks[eboot_patch.LANG_CFG_ID]
            self.ui.cboHackLang.setCurrentIndex(sys_lang)
        else:
            self.ui.cboHackLang.setCurrentIndex(0)

    def apply_hacks(self):
        for i in range(self.ui.lstHacks.count()):
            cfg_id = common.qt_to_unicode(
                self.ui.lstHacks.item(i).data(Qt.Qt.UserRole).toString())
            enabled = self.ui.lstHacks.item(i).checkState() == Qt.Qt.Checked

            if cfg_id:
                common.editor_config.hacks[cfg_id] = enabled

        common.editor_config.hacks[
            eboot_patch.LANG_CFG_ID] = self.ui.cboHackLang.currentIndex()

        return True


################################################################################
### SLOTS
################################################################################

    def button_clicked(self, button):
        if self.ui.buttonBox.buttonRole(
                button) == QtGui.QDialogButtonBox.ApplyRole:
            self.apply_settings()

    def apply_settings(self):
        if self.apply_prefs() and self.apply_file_locs() and self.apply_tags() and \
           self.apply_repl() and self.apply_hacks():

            common.editor_config.save_config()
            return True
        else:
            return False

    ##############################################################################
    ### @fn   accept()
    ### @desc Overrides the Save button.
    ##############################################################################
    def accept(self):
        if self.apply_settings() == False:
            return

        super(SettingsMenu, self).accept()

    ##############################################################################
    ### @fn   reject()
    ### @desc Overrides the Cancel button.
    ##############################################################################
    def reject(self):
        super(SettingsMenu, self).reject()