Example #1
0
    def onCommand(self, event):
        """Handle the slider reset command."""

        base.Widget.onCommand(self, event)

        if self.widgetId and event.hasId(self.resetCommand):
            pr.getActive().removeValue(self.widgetId)
Example #2
0
    def __getPresentation(self, tabId):
        """Compose the HTML presentation for a tab identifier.

        @return HTML content as a string.
        """
        # Kludge for the game-options icon.  There should be a way to
        # map the icon more flexibly so this hardcoding wouldn't be
        # needed.
        if tabId == "game-options":
            game = "game-jdoom"
            if pr.getActive():
                for c in pr.getActive().getComponents():
                    if c[:5] == "game-":
                        game = c
                        break
            imageName = language.translate(game + "-icon")
        else:
            imageName = language.translate(tabId + "-icon")

        return (
            '<table width="100%" border=0 cellspacing=3 cellpadding=1>'
            + "<tr><td width=35><img width=32 height=32 "
            + 'src="%s"></td><td align="left" valign="center">%s</td>'
            % (paths.findBitmap(imageName), language.translate(tabId))
            + "</tr></table>"
        )
Example #3
0
def handleNotify(event):
    """Handle a notification event."""

    global listenSelections

    if event.hasId('active-profile-changed'):
        refreshList()

    if event.hasId('maps-list-selected') and listenSelections:
        pr.getActive().useAddon(event.getSelection())

    if event.hasId('maps-list-deselected'):
        pr.getActive().dontUseAddon(event.getDeselection())

    if event.hasId('addon-attached'):
        listenSelections = False
        mapListBox.selectItem(event.getAddon())
        mapListBox.setItemImage(event.getAddon(), 1)
        listenSelections = True

    if event.hasId('addon-detached'):
        listenSelections = False
        mapListBox.deselectItem(event.getAddon())
        mapListBox.setItemImage(event.getAddon(), 0)
        listenSelections = True

    if event.hasId('addon-database-reloaded'):
        refreshList()

    if event.hasId('language-changed'):
        mapListBox.retranslateColumns()
Example #4
0
def handleNotify(event):
    """Handle a notification event."""

    global listenSelections

    if event.hasId('active-profile-changed'):
        refreshList()

    if event.hasId('maps-list-selected') and listenSelections:
        pr.getActive().useAddon(event.getSelection())

    if event.hasId('maps-list-deselected'):
        pr.getActive().dontUseAddon(event.getDeselection())

    if event.hasId('addon-attached'):
        listenSelections = False
        mapListBox.selectItem(event.getAddon())
        mapListBox.setItemImage(event.getAddon(), 1)
        listenSelections = True

    if event.hasId('addon-detached'):
        listenSelections = False
        mapListBox.deselectItem(event.getAddon())
        mapListBox.setItemImage(event.getAddon(), 0)
        listenSelections = True
        
    if event.hasId('addon-database-reloaded'):
        refreshList()
        
    if event.hasId('language-changed'):
        mapListBox.retranslateColumns()
Example #5
0
    def onCommand(self, event):
        """Handle the slider reset command."""
        
        base.Widget.onCommand(self, event)

        if self.widgetId and event.hasId(self.resetCommand):
            pr.getActive().removeValue(self.widgetId)
Example #6
0
    def onThumbTrack(self, ev):
        if self.widgetId:
            newValue = self.getValue()

            if newValue != self.oldValue:
                pr.getActive().setValue(self.widgetId, str(newValue))

                # Send a notification.
                events.send(events.EditNotify(self.widgetId, newValue))
                self.oldValue = newValue
Example #7
0
    def onThumbTrack(self, ev):
        if self.widgetId:
            newValue = self.getValue()

            if newValue != self.oldValue:
                pr.getActive().setValue(self.widgetId, str(newValue))

                # Send a notification.
                events.send(events.EditNotify(self.widgetId, newValue))
                self.oldValue = newValue
Example #8
0
def refreshItemInList(item):
    addon = ao.get(item)
    defaultAddons = pr.getDefaults().getAddons()
    if pr.getActive() is not pr.getDefaults():
        profileAddons = pr.getActive().getAddons()
    else:
        profileAddons = None
    
    # Update the image of the item.
    addonList.setItemImage(item, determineIcon(addon, pr.getActive(),
                                               defaultAddons, profileAddons))
Example #9
0
def refreshItemInList(item):
    addon = ao.get(item)
    defaultAddons = pr.getDefaults().getAddons()
    if pr.getActive() is not pr.getDefaults():
        profileAddons = pr.getActive().getAddons()
    else:
        profileAddons = None

    # Update the image of the item.
    addonList.setItemImage(
        item, determineIcon(addon, pr.getActive(), defaultAddons,
                            profileAddons))
Example #10
0
            def folderBrowseAction():
                # Open a folder browser for selecting the value for a file
                # setting.
                settingId = setting.getId()
                value = pr.getActive().getValue(settingId)
                if not value:
                    currentValue = ''
                else:
                    currentValue = value.getValue()

                selection = sb.util.dialog.chooseFolder(settingId + '-selection-title',
                                                        currentValue)

                if len(selection) > 0:
                    pr.getActive().setValue(settingId, selection)
Example #11
0
    def onNotify(self, event):
        base.Widget.onNotify(self, event)

        if self.widgetId and sb.confdb.isSettingDefined(self.widgetId):
            if event.hasId('active-profile-changed'):
                # Get the value for the setting as it has been defined
                # in the currently active profile.
                self.getFromProfile(pr.getActive())
Example #12
0
    def onNotify(self, event):
        base.Widget.onNotify(self, event)

        if self.widgetId and sb.confdb.isSettingDefined(self.widgetId):
            if event.hasId('active-profile-changed'):
                # Get the value for the setting as it has been defined
                # in the currently active profile.
                self.getFromProfile(pr.getActive())
Example #13
0
    def onClick(self, event):
        """Swap through the three states when the check box is clicked."""

        if self.widgetId:
            w = self.getWxWidget()
            state = w.Get3StateValue()

            if (state == wx.CHK_UNDETERMINED
                    and pr.getActive() is pr.getDefaults()):
                state = wx.CHK_UNCHECKED
                w.Set3StateValue(state)

            if state == wx.CHK_CHECKED:
                pr.getActive().setValue(self.widgetId, 'yes')
                newValue = 'yes'

            elif state == wx.CHK_UNCHECKED:
                pr.getActive().setValue(self.widgetId, 'no')
                newValue = 'no'

            else:
                pr.getActive().removeValue(self.widgetId)
                newValue = 'default'

            self.updateState()
            events.send(events.EditNotify(self.widgetId, newValue))

        # Let wxWidgets process the event, too.
        event.Skip()
Example #14
0
    def onClick(self, event):
        """Swap through the three states when the check box is clicked."""

        if self.widgetId:
            w = self.getWxWidget()
            state = w.Get3StateValue()

            if (state == wx.CHK_UNDETERMINED and 
                pr.getActive() is pr.getDefaults()):
                state = wx.CHK_UNCHECKED
                w.Set3StateValue(state)

            if state == wx.CHK_CHECKED:
                pr.getActive().setValue(self.widgetId, 'yes')
                newValue = 'yes'
                
            elif state == wx.CHK_UNCHECKED:
                pr.getActive().setValue(self.widgetId, 'no')
                newValue = 'no'

            else:
                pr.getActive().removeValue(self.widgetId)
                newValue = 'default'

            self.updateState()
            events.send(events.EditNotify(self.widgetId, newValue))
        
        # Let wxWidgets process the event, too.
        event.Skip()
Example #15
0
def handleCommand(event):
    if pr.getActive() is pr.getDefaults():
        return

    if event.hasId('play'):
        # Launch the game with the active profile.
        startGame(pr.getActive())

    elif event.hasId('continue') and resolving:
        continueResolving()

    elif event.hasId('view-command-line'):
        # Generate a command line and display it in a dialog.
        options = generateOptions(pr.getActive())
        if options == None:
            return

        # Escape any angle brackets.
        options = options.replace('<', '&lt;')
        options = options.replace('>', '&gt;')
        options = options.replace(' -', '<br>-')

        # Highlight all the options with a bold font.
        pos = 0
        while pos < len(options):
            if options[pos:pos + 5] == '<br>-' or \
                   pos == 0 and options[pos] == '-':
                options = options[:pos] + '<b>' + options[pos:]
                pos += 5
                while pos < len(options) and \
                      options[pos] not in string.whitespace:
                    pos += 1
                options = options[:pos] + '</b>' + options[pos:]
            pos += 1

        dialog, area = sb.util.dialog.createButtonDialog(
            'view-command-line-dialog',            
            ['ok'], 'ok')

        msg = area.createFormattedText()
        msg.setMinSize(500, 400)
        msg.setText('<tt>' + options + '</tt>')
        dialog.run()        
Example #16
0
def handleNotify(event):
    """This is called when somebody sends a notification.

    @param event A events.Notify object.
    """
    if event.hasId('show-help-text-now'):
        helpText.unfreeze()    
        return
    
    if helpDisabled:
        return
    
    if event.hasId('init-done'):
        setField(FIELD_MAIN, language.translate('help-welcome'))
        setField(FIELD_COMMAND, language.translate('help-command-defaults'))
        updateHelpText()    

    elif event.hasId('show-help-text-now'):
        helpText.unfreeze()
                        
    elif event.hasId('active-profile-changed'):
        if pr.getActive() is pr.getDefaults():
            setField(FIELD_COMMAND,
                     language.translate('help-command-defaults'))
        else:
            setField(FIELD_COMMAND, language.translate('help-command'))

    elif event.hasId('tab-selected'):
        setField(FIELD_MAIN, '')
        setField(FIELD_CURRENT_TAB,
                 language.translate('help-' + event.getSelection()))

    elif event.hasId('addon-list-selected') or \
         event.hasId('maps-list-selected'):
        # Display information about the selected addon in the panel.
        try:
            showAddonInfo(ao.get(event.getSelection()))
        except KeyError:
            # It wasn't an addon.
            pass

    elif event.hasId('focus-changed'): 
        try:
            setting = st.getSetting(event.getFocus())
            showSettingInfo(setting)
        except KeyError:
            # It was likely not a setting id.
            pass

    elif event.hasId('value-changed'):
        if currentSetting and event.getSetting() == currentSetting.getId():
            showSettingInfo(currentSetting)

    elif event.hasId('language-changed'):
        pass
Example #17
0
def handleNotify(event):
    """This is called when somebody sends a notification.

    @param event A events.Notify object.
    """
    if event.hasId('show-help-text-now'):
        helpText.unfreeze()
        return

    if helpDisabled:
        return

    if event.hasId('init-done'):
        setField(FIELD_MAIN, language.translate('help-welcome'))
        setField(FIELD_COMMAND, language.translate('help-command-defaults'))
        updateHelpText()

    elif event.hasId('show-help-text-now'):
        helpText.unfreeze()

    elif event.hasId('active-profile-changed'):
        if pr.getActive() is pr.getDefaults():
            setField(FIELD_COMMAND,
                     language.translate('help-command-defaults'))
        else:
            setField(FIELD_COMMAND, language.translate('help-command'))

    elif event.hasId('tab-selected'):
        setField(FIELD_MAIN, '')
        setField(FIELD_CURRENT_TAB,
                 language.translate('help-' + event.getSelection()))

    elif event.hasId('addon-list-selected') or \
         event.hasId('maps-list-selected'):
        # Display information about the selected addon in the panel.
        try:
            showAddonInfo(ao.get(event.getSelection()))
        except KeyError:
            # It wasn't an addon.
            pass

    elif event.hasId('focus-changed'):
        try:
            setting = st.getSetting(event.getFocus())
            showSettingInfo(setting)
        except KeyError:
            # It was likely not a setting id.
            pass

    elif event.hasId('value-changed'):
        if currentSetting and event.getSetting() == currentSetting.getId():
            showSettingInfo(currentSetting)

    elif event.hasId('language-changed'):
        pass
Example #18
0
def handleNotify(event):
    if event.hasId('active-profile-changed'):
        # Disable or enable controls based on which profile is selected.
        if pr.getActive() is pr.getDefaults():
            playButton.disable()
            ui.disableMenuCommand('play')
            ui.disableMenuCommand('view-command-line')
        else:
            playButton.enable()
            ui.enableMenuCommand('play')
            ui.enableMenuCommand('view-command-line')
Example #19
0
    def onItemSelected(self, ev):
        """Handle the wxWidgets event that is sent when the current
        selection changes in the list box.

        @param ev A wxWidgets event.
        """
        if self.widgetId:
            newSelection = self.items[ev.GetSelection()]

            if sb.confdb.isSettingDefined(self.widgetId):
                # This is a setting.
                if newSelection == 'default':
                    pr.getActive().removeValue(self.widgetId)
                else:
                    pr.getActive().setValue(self.widgetId, newSelection)

                # Notify everyone of the change.
                events.send(events.EditNotify(self.widgetId, newSelection))
            else:
                # Normal list.
                events.send(events.SelectNotify(self.widgetId, newSelection))
Example #20
0
            def browseAction():
                # Open a file browser for selecting the value for a file
                # setting.
                settingId = setting.getId()
                value = pr.getActive().getValue(settingId)
                if not value:
                    currentValue = ''
                else:
                    currentValue = value.getValue()

                selection = sb.util.dialog.chooseFile(
                    settingId + '-selection-title',
                    currentValue,
                    setting.hasToExist(),
                    setting.getAllowedTypes())

                if len(selection) > 0:
                    pr.getActive().setValue(settingId, selection)
                    if events.isMuted():
                        # Update manually.
                        text.getFromProfile(pr.getActive())
Example #21
0
    def onItemSelected(self, ev):
        """Handle the wxWidgets event that is sent when the current
        selection changes in the list box.

        @param ev A wxWidgets event.
        """
        if self.widgetId:
            newSelection = self.items[ev.GetSelection()]

            if sb.confdb.isSettingDefined(self.widgetId):
                # This is a setting.
                if newSelection == 'default':
                    pr.getActive().removeValue(self.widgetId)
                else:
                    pr.getActive().setValue(self.widgetId, newSelection)

                # Notify everyone of the change.
                events.send(events.EditNotify(self.widgetId, newSelection))
            else:
                # Normal list.
                events.send(events.SelectNotify(self.widgetId, newSelection))
Example #22
0
    def onNotify(self, event):
        """Notification listener.

        @param event An events.Notify object.
        """
        base.Widget.onNotify(self, event)

        if self.reactToNotify and event.hasId(self.widgetId + '-value-changed'):
            # This is our value.
            self.setText(event.getValue())

        if self.widgetId and event.hasId('active-profile-changed'):
            self.getFromProfile(pr.getActive())
Example #23
0
def handleNotify(event):
    """This is called when someone sends a notification event."""

    #if event.hasId('init-done'):

    if (event.hasId('value-changed') or
          event.hasId('active-profile-changed')):
        # Update any settings with value dependencies.
        enableByRequirements(pr.getActive())
        showCompatibleAddons(pr.getActive())

        # Only the defaults profile has the General category.
        if pr.getActive() is pr.getDefaults():
            wasIt = (categoryArea.getSelectedTab() == 'game-options')
            
            categoryArea.showTab('general-options')
            categoryArea.showTab('game-options', False)

            if wasIt:
                categoryArea.selectTab('general-options')
        else:
            wasIt = (categoryArea.getSelectedTab() == 'general-options')

            categoryArea.showTab('game-options')
            categoryArea.showTab('general-options', False)

            if wasIt:
                categoryArea.selectTab('game-options')

            categoryArea.updateIcon('game-options')

    elif event.hasId('addon-database-reloaded'):
        # Since the new addon will most likely introduce new settings,
        # we'll need to recreate the all the settings tabs.
        createWidgets()

        # The newly-created widgets don't have any data in them.  Make
        # them refresh their values.
        pr.refresh()
Example #24
0
    def onChange(self, ev):
        """Handle the wxWidgets event that is sent when the contents
        of the field changes."""
        if self.widgetId:
            if self.getWxWidget().IsInBounds():
                v = ev.GetValue()
                if v is not None:
                    newValue = str(v)
                else:
                    newValue = ''
            else:
                newValue = None

            self.reactToNotify = False
            if newValue == None:
                pr.getActive().removeValue(self.widgetId)
            else:
                pr.getActive().setValue(self.widgetId, newValue)
            self.reactToNotify = True

            # Notification about the change.
            events.sendAfter(events.EditNotify(self.widgetId, newValue))
Example #25
0
def notifyHandler(event):
    if summaryDisabled:
        return
    
    if event.hasId('active-profile-changed'):
        p = pr.getActive()
        titleLabel.setText(p.getName())

        # Update the summary entries.
        updateSummary(p)

        # Change to the Summary tab automatically.
        if event.hasId('active-profile-changed') and \
               st.getSystemBoolean('summary-profile-change-autoselect'):
            if event.wasChanged(): 
                # The profile did actually change.
                ui.selectTab(SUMMARY)

    elif event.hasId('value-changed') or \
         event.hasId('addon-attached') or \
         event.hasId('addon-detached'):
        # Resummarize due to a changed value of a setting.
        updateSummary(pr.getActive())
Example #26
0
def refreshList():
    """Fill the maps list with addons."""

    # Clear the list.
    mapListBox.clear()

    wads = [a for a in ao.getAvailableAddons(pr.getActive())
            if a.getType() == 'addon-type-wad' and a.isPWAD()]

    # Translate addon names.
    wads.sort(lambda a, b: cmp(a.getId(), b.getId()))

    for wad in wads:
        # TODO: More information titles.
        if not language.isDefined(wad.getId()):
            visibleName = language.translate(wad.getId())
        else:
            visibleName = os.path.basename(wad.getContentPath())
        mapListBox.addItemWithColumns(wad.getId(),
                                      0,
                                      visibleName,
                                      wad.getShortContentAnalysis())

    prof = pr.getActive()
    usedAddons = prof.getUsedAddons()
    theFirst = True

    # Select the addons currently attached to the profile.
    # Also make sure the first one is visible.
    for addonId in usedAddons:
        mapListBox.selectItem(addonId)
        mapListBox.setItemImage(addonId, 1)
        if theFirst:
            # Make sure it's visible.
            mapListBox.ensureVisible(addonId)
            theFirst = False
Example #27
0
    def __getPresentation(self, tabId):
        """Compose the HTML presentation for a tab identifier.

        @return HTML content as a string.
        """
        # Kludge for the game-options icon.  There should be a way to
        # map the icon more flexibly so this hardcoding wouldn't be
        # needed.
        if tabId == 'game-options':
            game = 'game-jdoom'
            if pr.getActive():
                for c in pr.getActive().getComponents():
                    if c[:5] == 'game-':
                        game = c
                        break
            imageName = language.translate(game + '-icon')
        else:
            imageName = language.translate(tabId + '-icon')

        return ('<table width="100%" border=0 cellspacing=3 cellpadding=1>' +
                '<tr><td width=35><img width=32 height=32 ' +
                'src="%s"></td><td align="left" valign="center">%s</td>' %
                (paths.findBitmap(imageName), language.translate(tabId)) +
                '</tr></table>')
Example #28
0
    def onTextChange(self, ev):
        """Handle the wxWidgets event that occurs when the contents of
        the field are updated (for any reason).

        @param ev wxWidgets event.
        """
        if self.willNotify and self.widgetId:
            newText = self.getWxWidget().GetValue()

            if not self.validator(newText):
                # The new text is not valid.  Nothing will be done.
                return

            self.reactToNotify = False
            if not len(newText):
                pr.getActive().removeValue(self.widgetId)
            else:
                pr.getActive().setValue(self.widgetId, newText)
            self.reactToNotify = True

            # Send a notification.
            events.sendAfter(events.EditNotify(self.widgetId, newText))

        self.react()
Example #29
0
def refreshList():
    """Fill the maps list with addons."""

    # Clear the list.
    mapListBox.clear()

    wads = [
        a for a in ao.getAvailableAddons(pr.getActive())
        if a.getType() == 'addon-type-wad' and a.isPWAD()
    ]

    # Translate addon names.
    wads.sort(lambda a, b: cmp(a.getId(), b.getId()))

    for wad in wads:
        # TODO: More information titles.
        if not language.isDefined(wad.getId()):
            visibleName = language.translate(wad.getId())
        else:
            visibleName = os.path.basename(wad.getContentPath())
        mapListBox.addItemWithColumns(wad.getId(), 0, visibleName,
                                      wad.getShortContentAnalysis())

    prof = pr.getActive()
    usedAddons = prof.getUsedAddons()
    theFirst = True

    # Select the addons currently attached to the profile.
    # Also make sure the first one is visible.
    for addonId in usedAddons:
        mapListBox.selectItem(addonId)
        mapListBox.setItemImage(addonId, 1)
        if theFirst:
            # Make sure it's visible.
            mapListBox.ensureVisible(addonId)
            theFirst = False
Example #30
0
    def onNotify(self, event):
        base.Widget.onNotify(self, event)
        
        if self.widgetId:
            if self.reactToNotify and event.hasId(self.widgetId + '-value-changed'):
                # This is our value.
                if event.getValue() != None:
                    self.setValue(int(event.getValue()))
                else:
                    self.setValue(None)

            elif event.hasId('active-profile-changed'):
                # Get the value for the setting as it has been defined
                # in the currently active profile.
                value = pr.getActive().getValue(self.widgetId, False)
                if value and value.getValue() != '':
                    self.setValue(int(value.getValue()))
                else:
                    self.setValue(None)
Example #31
0
    def onNotify(self, event):
        """Handle notifications.  When the active profile changes, the
        check box's state is updated."""

        base.Widget.onNotify(self, event)

        if self.widgetId:
            w = self.getWxWidget()
            if event.hasId('active-profile-changed'):
                self.getFromProfile(pr.getActive())

            elif event.hasId(self.widgetId + '-value-changed'):
                if event.getValue() == 'yes':
                    w.Set3StateValue(wx.CHK_CHECKED)
                elif event.getValue() == 'no':
                    w.Set3StateValue(wx.CHK_UNCHECKED)
                elif event.getValue() is None:
                    w.Set3StateValue(wx.CHK_UNDETERMINED)
                self.updateState()
Example #32
0
    def onNotify(self, event):
        """Handle notifications.  When the active profile changes, the
        check box's state is updated."""
        
        base.Widget.onNotify(self, event)

        if self.widgetId:
            w = self.getWxWidget()
            if event.hasId('active-profile-changed'):
                self.getFromProfile(pr.getActive())

            elif event.hasId(self.widgetId + '-value-changed'):
                if event.getValue() == 'yes':
                    w.Set3StateValue(wx.CHK_CHECKED)
                elif event.getValue() == 'no':
                    w.Set3StateValue(wx.CHK_UNCHECKED)
                elif event.getValue() is None:
                    w.Set3StateValue(wx.CHK_UNDETERMINED)
                self.updateState()
Example #33
0
    def retranslate(self):
        """Update all the items in the tree."""

        if pr.getActive():
            pass
Example #34
0
def runWizard():
    """Run the wizard dialog."""

    # Make sure the help panel isn't updated during the wizard.
    #events.send(events.Command('freeze'))

    suggested = {
        'doom1': 'DOOM.WAD',
        'doom1-share': 'DOOM1.WAD',
        'doom1-ultimate': 'DOOM.WAD',
        'doom2': 'DOOM2.WAD',
        'doom2-tnt': 'TNT.WAD',
        'doom2-plut': 'PLUTONIA.WAD',
        'heretic-ext': 'HERETIC.WAD',
        'heretic-share': 'HERETIC.WAD',
        'heretic': 'HERETIC.WAD',
        'hexen': 'HEXEN.WAD',
        'hexen-demo': 'HEXEN.WAD',
        'hexen-dk': 'HEXEN.WAD',
        'hacx': 'HACX.WAD',
        'chex': 'CHEX.WAD'
    }
    
    events.mute()
    
    # Make the Defaults profile active.
    pr.setActive(pr.getDefaults())
    
    wiz = WizardDialog(language.translate('setup-wizard'),
                       paths.findBitmap('wizard'))

    # Language selection page.
    langPage = WizardPage(wiz, 'wizard-language')
    area = langPage.getArea()
    area.createText('wizard-language-explanation', maxLineLength=65).resizeToBestSize()
    sar, languageCheckBox = area.createSetting(st.getSetting('language'))
    languageCheckBox.getFromProfile(pr.getActive())

    # Game selection.
    gamePage = ProfileWizardPage(wiz, 'wizard-games', None)
    gamePage.follows(langPage)
    area = gamePage.getArea()
    area.createText('wizard-select-games', maxLineLength=65).resizeToBestSize()
    area.setBorderDirs(ui.BORDER_NOT_BOTTOM)
    games = area.createList('', style=sb.widget.list.List.STYLE_CHECKBOX)
    area.setBorderDirs(ui.BORDER_NOT_TOP)
    games.setMinSize(50, 180)
    gamePage.setGameList(games)

    def allGames():
        # Check the entire list.
        for item in games.getItems():
            games.checkItem(item, True)

    def clearGames():
        # Uncheck the entire list.
        for item in games.getItems():
            games.checkItem(item, False)

    
    controls = area.createArea(alignment=ui.ALIGN_HORIZONTAL, border=2)
    controls.setWeight(0)
    button = controls.createButton('wizard-games-all', wb.Button.STYLE_MINI)
    button.addReaction(allGames)
    button.resizeToBestSize()
    button = controls.createButton('wizard-games-clear', wb.Button.STYLE_MINI)
    button.addReaction(clearGames)
    button.resizeToBestSize()

    # The pages will be linked together.
    previousPage = gamePage

    deathKingsWad = None

    # We'll do this dynamically.
    checkedProfiles = ['doom1', 'doom2', 'heretic', 'hexen']
    # Only display the system profiles in the wizard (not any user
    # profiles).
    profiles = pr.getProfiles(lambda p: p.isSystemProfile())
    for p in profiles:
        if p is not pr.getDefaults():
            games.addItem(p.getId(), p.getId() in checkedProfiles)

            # Create a page for the profile.
            page = ProfileWizardPage(wiz, p.getId(), games)

            # Link the pages together.
            page.follows(previousPage)
            previousPage = page
            
            area = page.getArea()

            area.createText('wizard-locate-iwad', maxLineLength=65).resizeToBestSize()

            # The suggestion.
            if suggested.has_key(p.getId()):
                sugArea = area.createArea(alignment=ui.ALIGN_HORIZONTAL, border=2)
                sugArea.setExpanding(False)
                sugArea.setWeight(1)
                sugArea.createText('wizard-suggested-iwad', ':', align=wt.Text.RIGHT)
                sugArea.setWeight(2)
                sug = sugArea.createText('')
                sug.setText(suggested[p.getId()])

            sar, page.iwadText = area.createSetting(st.getSetting('iwad'))

            if p.getId() == 'hexen-dk':
                area.setBorder(12, ui.BORDER_ALL)
                area.createLine()
                area.setBorder(6, ui.BORDER_ALL)
                area.createText('deathkings-selection-title').setHeadingStyle()
                
                # Death Kings is an extension to Hexen.  It uses the
                # same Hexen IWAD, but also an addon IWAD.
                area.createText('wizard-locate-iwad-deathkings', maxLineLength=65).resizeToBestSize()

                entry = area.createArea(alignment=ui.ALIGN_HORIZONTAL, border=4)
                entry.setExpanding(False)
                entry.setWeight(1)
                entry.setBorderDirs(ui.BORDER_NOT_LEFT)
                deathKingsWad = entry.createTextField('')
                entry.setWeight(0)
                entry.setBorderDirs(ui.BORDER_TOP_BOTTOM)
                browseButton = entry.createButton('browse-button', wb.Button.STYLE_MINI)

                def browseDeathKings():
                    # Open a file browser.
                    selection = sb.util.dialog.chooseFile('deathkings-selection-title',
                                                          '', True,
                                                          [('file-type-wad', 'wad')])
                
                    if len(selection) > 0:
                        deathKingsWad.setText(selection)

                browseButton.addReaction(browseDeathKings)

	# Addon paths.
	pathsPage = ProfileWizardPage(wiz, 'wizard-addon-paths', games)
	pathsPage.follows(previousPage)
	area = pathsPage.getArea()
	area.createText('wizard-addon-paths-explanation',
                    maxLineLength=65).resizeToBestSize()

    area.setBorderDirs(ui.BORDER_NOT_BOTTOM)
    pathList = area.createList('addon-paths-list')
    pathList.setMinSize(100, 120)

    # Insert the current custom paths into the list.
    for p in paths.getAddonPaths():
        pathList.addItem(p)

    def addAddonPath():
        selection = sb.util.dialog.chooseFolder('addon-paths-add-prompt', '')
        if selection:
            pathList.addItem(selection)
            pathList.selectItem(selection)

    def removeAddonPath():
        selection = pathList.getSelectedItem()
        if selection:
            pathList.removeItem(selection)

    area.setWeight(0)
    area.setBorderDirs(ui.BORDER_NOT_TOP)
    commands = area.createArea(alignment=ui.ALIGN_HORIZONTAL, border=2)
    commands.setWeight(0)

    # Button for adding new paths.
    button = commands.createButton('new-addon-path', wb.Button.STYLE_MINI)
    button.addReaction(addAddonPath)

    # Button for removing a path.
    button = commands.createButton('delete-addon-path', wb.Button.STYLE_MINI)
    button.addReaction(removeAddonPath)

    # Launch options.
    quitPage = WizardPage(wiz, 'wizard-launching') 
    quitPage.follows(pathsPage)
    area = quitPage.getArea()
    area.createText('wizard-launching-explanation').resizeToBestSize()
    sar, quitCheckBox = area.createSetting(st.getSetting('quit-on-launch'))
    quitCheckBox.getFromProfile(pr.getActive())

    # List of unusable profiles, due to a missing IWAD.
    unusableProfiles = []
    
    # When the page changes in the wizard, change the active profile.
    def changeActiveProfile(page):
        prof = pr.get(page.getId())
        if prof:
            pr.setActive(prof)
        else:
            pr.setActive(pr.getDefaults())
        # Update page with values from the current profile.
        page.update()
                       
    wiz.setPageReaction(changeActiveProfile)
    
    if wiz.run(langPage) == 'ok':
        events.unmute()
        
        # Show the profiles that now have an IWAD.
        for prof in profiles:
            if prof.getValue('iwad', False) != None:
                pr.show(prof.getId())
                if prof.getId() in unusableProfiles:
                    unusableProfiles.remove(prof.getId())
            else:
                pr.hide(prof.getId())
                if prof.getId() not in unusableProfiles and \
                   prof.getId() in games.getSelectedItems():
                    unusableProfiles.append(prof.getId())

        # Install the Death Kings WAD?
        if deathKingsWad:
            try:
                ident = ao.install(deathKingsWad.getText())

                # Attach the WAD as an addon.
                kingsProfile = pr.get('hexen-dk')
                kingsProfile.useAddon(ident)
            except:
                # TODO: Handle error.
                pass

        # Update custom addon paths.
        currentAddonPaths = paths.getAddonPaths()
        wasModified = False
        for path in pathList.getItems():
            if path not in currentAddonPaths:
                paths.addAddonPath(path)
                wasModified = True
        for path in currentAddonPaths:
            if path not in pathList.getItems():
                paths.removeAddonPath(path)
                wasModified = True

        if wasModified:
            # Load addons from new paths.
            ao.refresh()

        events.send(events.Notify('addon-paths-changed'))

        # The wizard will only be shown once automatically.
        pr.getDefaults().setValue(HAS_BEEN_RUN, 'yes', False)

    else:
        # Wizard was canceled.
        events.unmute()

    pr.refresh()

    # This'll destroy all the pages of the wizard as well.
    wiz.destroy()

    # Enable help panel updates again.
    #events.send(events.Command('unfreeze'))
    
    # Tell the user about unusable profiles.
    if len(unusableProfiles) > 0:
        dialog, area = sb.util.dialog.createButtonDialog(
            'wizard-unlaunchable-profiles',
            ['ok'], 'ok', resizable=False)
        # Compose a list of the unlaunchable profiles.
        profList = ''
        unusableProfiles.sort(lambda a, b: cmp(language.translate(a),
                                               language.translate(b)))
        for p in unusableProfiles:
            profList += "\n" + language.translate(p)
        msg = area.createText()
        msg.setText(language.translate('wizard-unlaunchable-profiles-listed') + "\n" + 
                    profList)
        msg.resizeToBestSize()
        dialog.run()
def notifyHandler(event):
    "This is called when a Notify event is broadcasted."

    # We are interested in notifications that concern profiles.
    if event.hasId('quit'):
        # Save the current profile configuration.
        pr.save()

    elif event.hasId('language-changed'):
        # Just update the Defaults, because it's the only profile whose name
        # is translated.
        addListItem(pr.getDefaults())

    elif event.hasId('profile-updated'):
        # A profile has been loaded or updated.  Make sure it's in the
        # list.
        p = event.getProfile()

        # The Defaults profile should be first in the list.
        if p is pr.getDefaults():
            destIndex = 0
        else:
            # The new profile will be added to wherever the widget
            # wants to put it.
            destIndex = None

        if profileList.hasItem(p.getId()):
            # This already exists in the list.
            if p.isHidden():
                # Remove it completely.
                profileList.removeItem(p.getId())

                # Update the selected item since the active one is now
                # hidden.
                pr.setActive(pr.get(profileList.getSelectedItem()))
            else:
                # Just update the item.
                addListItem(p)

        elif not p.isHidden():
            # The item does not yet exist in the list.
            addListItem(p, toIndex=destIndex)

    elif event.hasId('active-profile-changed') and not profileListDisabled:
        # Highlight the correct profile in the list.
        profileList.selectItem(pr.getActive().getId())

        if pr.getActive() is pr.getDefaults():
            if deleteButton: deleteButton.disable()
            if dupeButton: dupeButton.disable()
            ui.disableMenuCommand('rename-profile')
            ui.disableMenuCommand('delete-profile')
            ui.disableMenuCommand('hide-profile')
            ui.disableMenuCommand('duplicate-profile')
            profileList.setPopupMenu(defaultsMenu)
        else:
            isSystem = pr.getActive().isSystemProfile()
            if deleteButton: deleteButton.enable(not isSystem)
            if dupeButton: dupeButton.enable()
            ui.enableMenuCommand('rename-profile')
            ui.enableMenuCommand('delete-profile', not isSystem)
            ui.enableMenuCommand('hide-profile')
            ui.enableMenuCommand('duplicate-profile')
            if isSystem:
                menu = systemMenu
            else:
                menu = normalMenu
            profileList.setPopupMenu(menu)

        # Update the banner image.
        if bannerImage:
            bannerImage.setImage(pr.getActive().getBanner())

    elif event.hasId('profile-list-selected'):
        # Change the currently active profile.
        p = pr.get(event.getSelection())
        pr.setActive(p)

        # Double-clicking causes a Play command.
        if event.isDoubleClick() and p is not pr.getDefaults():
            events.sendAfter(events.Command('play'))
Example #36
0
def handleCommand(event):
    """This is called when someone sends a command event.

    @param event An events.Command object."""

    # Figure out which addon has been currently selected in the addons
    # tree.  The action will target this addon.
    selected = ''

    if event.hasId('refresh-addon-database'):
        ao.refresh()

    elif event.hasId('install-addon'):
        tab30.installer.run()

    elif event.hasId('uninstall-addon'):
        selectedItems = addonList.getSelectedItems()
                
        # Only take the uninstallable addons.
        addons = filter(lambda i: ao.isUninstallable(i), selectedItems)
        if len(addons) == 0:
            return
            
        # Make sure the user wants to uninstall.
        dialog, area = sb.util.dialog.createButtonDialog(
            'uninstall-addon-dialog',
            ['no', 'yes'], 'no', resizable=False)

        if len(addons) == 1:
            text = language.translate('uninstall-addon-query')
            area.setExpanding(True)
            area.createRichText(language.expand(text, language.translate(addons[0])))
        else:
            area.setWeight(0)
            area.createText('uninstall-addon-query-several')
            msg = '<html><ul>'
            for addon in addons:
                msg += '<li>' + language.translate(addon) + '</li>'
            msg += '</ul></html>'
            ft = area.createFormattedText()
            ft.setText(msg)
            ft.setMinSize(400, 150)
    
        if dialog.run() == 'yes':
            for addon in addons:
                ao.uninstall(addon)
            ao.refresh()

    elif event.hasId('addon-info'):
        sel = addonList.getSelectedItems()
        if len(sel) > 0:
            # Show the Addon Inspector.
            tab30.inspector.run(ao.get(sel[0]))

    elif event.hasId('addon-settings'):
        sel = addonList.getSelectedItems()
        if len(sel) > 0:
            command = events.Command('show-addon-settings')
            command.addon = sel[0]
            events.send(command)        

    elif event.hasId('load-order'):
        # Open the Load Order dialog.
        tab30.loadorder.run(pr.getActive())

    elif event.hasId('addon-list-check-selected'):
        for addon in addonList.getSelectedItems():
            pr.getActive().useAddon(addon)

    elif event.hasId('addon-list-uncheck-selected'):
        for addon in addonList.getSelectedItems():
            pr.getActive().dontUseAddon(addon)

    elif event.hasId('addon-list-check-all'):
        for addon in addonList.getItems():
            pr.getActive().useAddon(addon)

    elif event.hasId('addon-list-uncheck-all'):
        for addon in addonList.getItems():
            pr.getActive().dontUseAddon(addon)
            
    elif event.hasId('addon-show-parent-box'):
        for addon in addonList.getSelectedItems():
            a = ao.get(addon)
            if a.getBox():
                showInAddonList(a.getBox().getId())
            break
            
    elif event.hasId('addon-show-box-category'):
        for addon in addonList.getSelectedItems():
            a = ao.get(addon)
            if a.getType() == 'addon-type-box':
                addonList.deselectAllItems()
                tree.selectItem(a.getContentCategoryLongId())
                refreshListIfVisible()
            break
Example #37
0
def showSettingInfo(setting):
    """Display information about the focused setting in the help
    panel.

    @param setting A settings.Setting object.
    """
    # Values will be taken from the active profile.
    prof = pr.getActive()

    # The identifier of the setting.
    ident = setting.getId()

    msg = '<html>'

    # The name of the setting.
    msg += '<b><font size="+1">' + language.translate(ident) + \
           '</font></b>'

    # The command line option.
    msg += '<br><table bgcolor="' + bgColor + '" width="100%"><tr><td>' + \
           '<font size="-1"><tt>' + \
           setting.getCommandLine(prof) + '</tt></font></table><p>'

    fromDefaults = False

    if prof.getValue(ident, False) == None:
        fromDefaults = True
        # The value comes from the default profile.
        msg += language.expand(language.translate('help-value-from-defaults'),
                               pr.getDefaults().getName()) + '<p>'

    def valueToText(v):
        if language.isDefined(v):
            return language.translate(v)
        else:
            return v

    msg += tableBegin

    # The current value of the setting.
    value = prof.getValue(ident)
    if value:
        #msg += '<b>%s:</b><br>' % language.translate('help-value-current')
        #msg += valueToText(value.getValue())
        #msg += '<p>'

        msg += tableRow + \
               entryHeader(language.translate('help-value-current')) + \
               entryContent(valueToText(value.getValue()))

    # Min and max for the range and slider settings.
    if setting.getType() == 'slider' or setting.getType() == 'range':
        #msg += '<b>' + language.translate('help-value-min') + ':</b><br>' + \
        #       str(setting.getMinimum())
        #msg += '<p><b>' + language.translate('help-value-max') + \
        #       ':</b><br>' + str(setting.getMaximum())
        #msg += '<p>'

        msg += tableRow + entryHeader(language.translate('help-value-min')) + \
               entryContent(str(setting.getMinimum())) + \
               tableRow + entryHeader(language.translate('help-value-max')) + \
               entryContent(str(setting.getMaximum()))

    # The default.
    if prof.getValue(ident, False) != None and prof is pr.getDefaults():
        if setting.getDefault() != None:
            #msg += '<b>%s:</b><br>' % language.translate('help-value-default')
            #msg += valueToText(str(setting.getDefault()))
            #msg += '<p>'

            msg += tableRow + \
                   entryHeader(language.translate('help-value-default')) + \
                   entryContent(valueToText(str(setting.getDefault())))

    elif not fromDefaults and prof is not pr.getDefaults():
        defValue = pr.getDefaults().getValue(ident)
        if defValue:
            #msg += '<b>%s:</b><br>' % language.translate('help-value-default')
            #msg += valueToText(defValue.getValue())
            #msg += '<p>'

            msg += tableRow + \
                   entryHeader(language.translate('help-value-default')) + \
                   entryContent(valueToText(defValue.getValue()))

    msg += tableEnd

    # The help text of this setting.
    helpId = ident + '-help'
    if language.isDefined(helpId):
        msg += language.translate(helpId)

    msg += '</html>'

    # Display the setting information in the help panel.
    helpText.setText(msg)
    showLogo(False)

    # The info will be automatically updated in case it changes while
    # displayed.
    global currentSetting
    currentSetting = setting
Example #38
0
    def doCreateSetting(self, setting,
                        leftWeight=SETTING_WEIGHT_LEFT,
                        rightWeight=SETTING_WEIGHT_RIGHT):
        """Create one or more widgets that can be used to edit the
        value of the specified setting.  Automatically creates a
        subarea that contains all the widgets of the setting.

        @param setting A Setting object.

        @return  Tuple (area, widget). The area which contains all the widgets
                 of the setting, and the main widget of the setting.
        """
        if setting.getType() == 'implicit':
            # No widgets for implicit settings.
            return (None, None)

        # This is the returned main widget of the setting.
        mainWidget = None

        # Create a subarea for all the widgets of the setting.
        area = self.createArea(alignment=ui.ALIGN_HORIZONTAL)
        area.setExpanding(False)

        # All settings have a similarly positioned label on the left
        # side.
        area.setWeight(leftWeight)

        if setting.getType() != 'toggle':
            area.createText(setting.getId(), ':', 16, sb.widget.text.Text.RIGHT)
        else:
            # Check boxes use a secondary indicator label.
            label = area.createText('toggle-use-default-value',
                                    align=sb.widget.text.Text.RIGHT)

        area.setWeight(0)
        area.setBorder(2) # Space between label and setting.
        area.addSpacer()
        area.setBorder(0)

        # Create the actual widget(s) for the setting.
        area.setWeight(rightWeight)

        if setting.getType() == 'toggle':
            # Toggle settings have just a checkbox.
            isChecked = False
            if pr.getActive():
                isChecked = (pr.getActive().getValue(setting.getId()).
                             getValue() == 'yes')
            check = area.createCheckBox(setting.getId(), isChecked)
            check.setDefaultIndicator(label)
            mainWidget = check

        elif setting.getType() == 'range':
            nf = area.createNumberField(setting.getId())
            nf.setRange(setting.getMinimum(), setting.getMaximum())
            mainWidget = nf

        elif setting.getType() == 'slider':
            slider = area.createSlider(setting.getId())
            slider.setRange(setting.getMinimum(),
                            setting.getMaximum(),
                            setting.getStep())
            mainWidget = slider

        elif setting.getType() == 'choice':
            # Create a label and a drop-down list.
            drop = area.createDropList(setting.getId())
            mainWidget = drop

            # Insert the choices into the list.
            drop.addItem('default')
            for a in setting.getAlternatives():
                drop.addItem(a)

            # Sort if necessary.
            if setting.isSorted():
                drop.sortItems()

            # The selection will be updated soon afterwards.
            drop.selectItem('default')

        elif setting.getType() == 'text':
            text = area.createTextField(setting.getId())
            mainWidget = text

        elif setting.getType() == 'file':
            # Create a text field and a button.
            sub = area.createArea(alignment=ui.ALIGN_HORIZONTAL, border=0)
            sub.setWeight(1)
            text = sub.createTextField(setting.getId())
            mainWidget = text
            sub.setWeight(0)
            sub.setBorder(4, ui.BORDER_LEFT)
            browseButton = sub.createButton('browse-button',
                                            style=sb.widget.button.Button.STYLE_MINI)

            def browseAction():
                # Open a file browser for selecting the value for a file
                # setting.
                settingId = setting.getId()
                value = pr.getActive().getValue(settingId)
                if not value:
                    currentValue = ''
                else:
                    currentValue = value.getValue()

                selection = sb.util.dialog.chooseFile(
                    settingId + '-selection-title',
                    currentValue,
                    setting.hasToExist(),
                    setting.getAllowedTypes())

                if len(selection) > 0:
                    pr.getActive().setValue(settingId, selection)
                    if events.isMuted():
                        # Update manually.
                        text.getFromProfile(pr.getActive())

            browseButton.addReaction(browseAction)

            # If the file must exist, don't accept nonexistent files.
            if setting.hasToExist():
                text.setValidator(lambda fileName: os.path.exists(fileName))

        elif setting.getType() == 'folder':
            # Create a text field and a button, like with a file setting.
            sub = area.createArea(alignment=ui.ALIGN_HORIZONTAL, border=0)
            sub.setWeight(1)
            text = sub.createTextField(setting.getId())
            mainWidget = text
            sub.setWeight(0)
            browseButton = sub.createButton('browse-button',
                                            style=sb.widget.button.Button.STYLE_MINI)

            def folderBrowseAction():
                # Open a folder browser for selecting the value for a file
                # setting.
                settingId = setting.getId()
                value = pr.getActive().getValue(settingId)
                if not value:
                    currentValue = ''
                else:
                    currentValue = value.getValue()

                selection = sb.util.dialog.chooseFolder(settingId + '-selection-title',
                                                        currentValue)

                if len(selection) > 0:
                    pr.getActive().setValue(settingId, selection)

            browseButton.addReaction(folderBrowseAction)

            # If the file must exist, don't accept nonexistent files.
            if setting.hasToExist():
                text.setValidator(lambda fileName: os.path.exists(fileName))

        return (area, mainWidget)
Example #39
0
def handleNotification(event):
    """This is called when someone sends a notification event.

    @param event An events.Notify object.
    """
    global tabVisible
    global mustRefreshList

    if event.hasId('addon-list-icon-click'):
        # Clicking on the list icon will attach/detach the addon.
        profile = pr.getActive()
        if event.item in profile.getUsedAddons():
            profile.dontUseAddon(event.item)
        else:
            profile.useAddon(event.item)

    elif event.hasId('addon-attached') or event.hasId('addon-detached'):
        refreshItemInList(event.getAddon())

    elif event.hasId('addon-list-filter-mode-selected'):
        refreshListIfVisible()

    elif event.hasId('addon-list-check-column-click') or \
         event.hasId('addon-list-name-column-click') or \
         event.hasId('addon-list-version-column-click'):
        global listSortMode
        if 'check' in event.getId():
            listSortMode = 'check'
        elif 'version' in event.getId():
            listSortMode = 'version'
        else:
            listSortMode = 'name'
        sortList()

    elif event.hasId('tab-selected'):
        # If there is a refresh pending, do it now that the tab has
        # been selected.
        if event.getSelection() == ADDONS:
            tabVisible = True
            if mustRefreshList:
                refreshList()
        else:
            tabVisible = False

    elif event.hasId('active-profile-changed'):
        refreshListIfVisible()

        # Fill the tree with an updated listing of addons.
        #tree.populateWithAddons(pr.getActive())
        #settingsButton.disable()

    elif event.hasId('addon-list-popup-update-request'):
        # The addon list is requesting an updated popup menu.
        # Menu items depend on which items are selected.
        items = addonList.getSelectedItems()
        menu = []

        if len(items) == 1:
            # One addon is selected.
            if ao.get(items[0]).getBox():
                menu += ['addon-show-parent-box']
            if ao.get(items[0]).getType() == 'addon-type-box':
                menu += ['addon-show-box-category']
            # Info is always available for all addons.
            menu += ['addon-info']
            if st.haveSettingsForAddon(items[0]):
                menu += ['addon-settings']
        elif len(items) > 1:
            # Multiple addons selected.
            menu += [
                'addon-list-check-selected', 'addon-list-uncheck-selected'
            ]

        if len(items) > 0: menu += ['uninstall-addon']

        # Append the common items.
        if len(menu) > 0: menu.append('-')
        menu += ['install-addon']
        menu += ['load-order']

        menu += ['-', 'addon-list-check-all', 'addon-list-uncheck-all']

        addonList.setPopupMenu(menu)

    elif event.hasId('category-tree-selected'):
        refreshListIfVisible()
        # Enable the settings button if there are settings for this
        # addon.
        #if st.haveSettingsForAddon(event.getSelection()):
        #    settingsButton.enable()
        #else:
        #    settingsButton.disable()

        # Can this be uninstalled?
        #uninstallButton.enable(ao.exists(event.getSelection()) and
        #                       ao.get(event.getSelection()).getBox() == None)

    elif event.hasId('addon-list-selected') or event.hasId(
            'addon-list-deselected'):
        updateButtons()

    elif event.hasId('addon-installed'):
        refreshCategories()
        refreshListIfVisible()
        #tree.selectAddon(event.addon)

    elif event.hasId('addon-database-reloaded'):
        refreshCategories()
        refreshListIfVisible()
def commandHandler(event):
    """This is called when a Command event is broadcasted."""

    global profileListDisabled

    if event.hasId('freeze'):
        profileListDisabled = True

    elif event.hasId('unfreeze'):
        profileListDisabled = False
        #notifyHandler(events.Notify('active-profile-changed'))
        pr.refresh()

    elif event.hasId('new-profile'):
        dialog, area = sb.util.dialog.createButtonDialog('new-profile-dialog',
                                                         ['cancel', 'ok'],
                                                         'ok',
                                                         resizable=False)
        dialog.disableWidget('ok')

        entry = area.createArea(alignment=ALIGN_HORIZONTAL)
        entry.setExpanding(False)

        # The name of the profile.
        entry.setWeight(1)
        entry.setBorder(4, ui.BORDER_RIGHT)
        entry.createText('new-profile-name', ':', align=wt.Text.RIGHT)
        entry.setBorder(0)
        entry.setWeight(2)
        nameField = entry.createTextField('')
        nameField.focus()

        # Only enable the OK button if there is something in the name field.
        def buttonEnabler():
            dialog.enableWidget('ok', len(nameField.getText()) > 0)

        nameField.addReaction(buttonEnabler)

        # The game component.
        entry = area.createArea(alignment=ALIGN_HORIZONTAL)
        entry.setExpanding(False)

        entry.setWeight(1)
        entry.setBorder(4, ui.BORDER_RIGHT)
        entry.createText('new-profile-game', ':', align=wt.Text.RIGHT)
        entry.setBorder(0)
        entry.setWeight(2)
        gameDrop = entry.createDropList('')

        for game in st.getGameComponents():
            gameDrop.addItem(game.getId())

        gameDrop.sortItems()

        # Select the first one.
        gameDrop.selectItem(gameDrop.getItems()[0])

        if dialog.run() == 'ok':
            # Get the values from the controls.
            pr.create(nameField.getText(), gameDrop.getSelectedItem())

    elif event.hasId('rename-profile'):
        dialog, area = sb.util.dialog.createButtonDialog(
            'rename-profile-dialog', ['cancel', 'ok'], 'ok', resizable=False)

        prof = pr.getActive()

        # A text field of the new name.
        entry = area.createArea(alignment=ALIGN_HORIZONTAL)
        entry.setExpanding(False)

        # The name of the profile.
        entry.setWeight(1)
        entry.setBorder(4, ui.BORDER_RIGHT)
        entry.createText('rename-profile-name', ':', align=wt.Text.RIGHT)
        entry.setBorder(0)
        entry.setWeight(2)
        nameField = entry.createTextField('')
        nameField.setText(prof.getName())
        nameField.focus()

        # Only enable the OK button if there is something in the name
        # field.
        def buttonEnabler():
            dialog.enableWidget('ok', len(nameField.getText()) > 0)

        nameField.addReaction(buttonEnabler)

        if dialog.run() == 'ok':
            prof.setName(nameField.getText())
            # The profile list needs to be updated, too.
            events.send(events.ProfileNotify(prof))
            pr.refresh()

    elif event.hasId('reset-profile'):
        dialog, area = sb.util.dialog.createButtonDialog(
            'reset-profile-dialog', [
                'cancel', 'reset-profile-values', 'reset-profile-addons',
                'reset-profile-everything'
            ],
            'cancel',
            resizable=False)

        text = language.translate('reset-profile-query')
        message = area.createRichText(
            language.expand(text,
                            pr.getActive().getName()))

        # Accept these as dialog-closing commands.
        dialog.addEndCommand('reset-profile-values')
        dialog.addEndCommand('reset-profile-addons')
        dialog.addEndCommand('reset-profile-everything')

        result = dialog.run()
        if result == 'cancel':
            return

        resetValues = True
        resetAddons = True
        if result == 'reset-profile-values':
            resetAddons = False
        elif result == 'reset-profile-addons':
            resetValues = False
        pr.reset(pr.getActive().getId(), resetValues, resetAddons)
        pr.refresh()

    elif event.hasId('delete-profile'):
        # If this is a system profile, just hide it.
        if pr.getActive().isSystemProfile():
            pr.hide(pr.getActive().getId())
            return

        dialog, area = sb.util.dialog.createButtonDialog(
            'delete-profile-dialog', ['no', 'yes'], 'no', resizable=False)

        text = language.translate('delete-profile-query')
        area.createRichText(language.expand(text, pr.getActive().getName()))

        if dialog.run() == 'yes':
            # Get the values from the controls.
            pr.remove(pr.getActive().getId())

    elif event.hasId('duplicate-profile'):
        dialog, area = sb.util.dialog.createButtonDialog(
            'duplicate-profile-dialog', ['cancel', 'ok'],
            'ok',
            resizable=False)

        text = language.translate('duplicating-profile')
        area.setWeight(1)
        area.createRichText(language.expand(text, pr.getActive().getName()))

        area.setWeight(1)
        entry = area.createArea(alignment=ALIGN_HORIZONTAL)
        entry.setExpanding(False)

        # The name of the profile.
        entry.setWeight(1)
        entry.setBorder(4, ui.BORDER_RIGHT)
        entry.createText('new-profile-name', ':', align=wt.Text.RIGHT)
        entry.setBorder(0)
        entry.setWeight(3)
        nameField = entry.createTextField('')
        nameField.setText(pr.getActive().getName())
        nameField.focus()

        # Only enable the OK button if there is something in the name field.
        def buttonEnabler():
            dialog.enableWidget('ok', len(nameField.getText()) > 0)

        nameField.addReaction(buttonEnabler)

        if dialog.run() == 'ok':
            pr.duplicate(pr.getActive().getId(), nameField.getText())

    elif event.hasId('hide-profile'):
        pr.hide(pr.getActive().getId())

    elif event.hasId('unhide-profiles'):
        # Display a dialog bog for unhiding hidden profiles.
        hiddenProfiles = pr.getProfiles(lambda p: p.isHidden())

        dialog, area = sb.util.dialog.createButtonDialog(
            'unhide-profile-dialog', ['cancel', 'ok'], 'ok', resizable=False)

        area.setWeight(0)
        area.createText('unhiding-profiles')

        area.setWeight(3)
        area.setBorder(0)
        profList = area.createList('', sb.widget.list.List.STYLE_CHECKBOX)
        profList.setMinSize(50, 150)

        def selectAll():
            # Check the entire list.
            for item in profList.getItems():
                profList.checkItem(item, True)

        def clearAll():
            # Uncheck the entire list.
            for item in profList.getItems():
                profList.checkItem(item, False)

        area.setWeight(0)
        controls = area.createArea(alignment=ALIGN_HORIZONTAL, border=2)
        controls.setWeight(0)
        button = controls.createButton(
            'unhide-select-all', style=sb.widget.button.Button.STYLE_MINI)
        button.addReaction(selectAll)
        button.resizeToBestSize()
        button = controls.createButton(
            'unhide-clear-all', style=sb.widget.button.Button.STYLE_MINI)
        button.addReaction(clearAll)
        button.resizeToBestSize()

        for prof in hiddenProfiles:
            profList.addItem(prof.getId())

        if dialog.run() == 'ok':
            # Unhide all the selected items.
            selected = profList.getSelectedItems()
            for sel in selected:
                pr.show(sel)

            if len(selected):
                # Select the first one that was shown.
                pr.setActive(pr.get(selected[0]))
Example #41
0
def showSettingInfo(setting):
    """Display information about the focused setting in the help
    panel.

    @param setting A settings.Setting object.
    """
    # Values will be taken from the active profile.
    prof = pr.getActive()

    # The identifier of the setting.
    ident = setting.getId()
    
    msg = '<html>'

    # The name of the setting.
    msg += '<b><font size="+1">' + language.translate(ident) + \
           '</font></b>'

    # The command line option.
    msg += '<br><table bgcolor="' + bgColor + '" width="100%"><tr><td>' + \
           '<font size="-1"><tt>' + \
           setting.getCommandLine(prof) + '</tt></font></table><p>'

    fromDefaults = False

    if prof.getValue(ident, False) == None:
        fromDefaults = True
        # The value comes from the default profile.
        msg += language.expand(
            language.translate('help-value-from-defaults'),
            pr.getDefaults().getName()) + '<p>'

    def valueToText(v):
        if language.isDefined(v):
            return language.translate(v)
        else:
            return v

    msg += tableBegin

    # The current value of the setting.
    value = prof.getValue(ident)
    if value:
        #msg += '<b>%s:</b><br>' % language.translate('help-value-current')
        #msg += valueToText(value.getValue())
        #msg += '<p>'

        msg += tableRow + \
               entryHeader(language.translate('help-value-current')) + \
               entryContent(valueToText(value.getValue()))

    # Min and max for the range and slider settings.
    if setting.getType() == 'slider' or setting.getType() == 'range':
        #msg += '<b>' + language.translate('help-value-min') + ':</b><br>' + \
        #       str(setting.getMinimum())
        #msg += '<p><b>' + language.translate('help-value-max') + \
        #       ':</b><br>' + str(setting.getMaximum())
        #msg += '<p>'

        msg += tableRow + entryHeader(language.translate('help-value-min')) + \
               entryContent(str(setting.getMinimum())) + \
               tableRow + entryHeader(language.translate('help-value-max')) + \
               entryContent(str(setting.getMaximum()))

    # The default.
    if prof.getValue(ident, False) != None and prof is pr.getDefaults():
        if setting.getDefault() != None:
            #msg += '<b>%s:</b><br>' % language.translate('help-value-default')
            #msg += valueToText(str(setting.getDefault()))
            #msg += '<p>'

            msg += tableRow + \
                   entryHeader(language.translate('help-value-default')) + \
                   entryContent(valueToText(str(setting.getDefault())))
            
    elif not fromDefaults and prof is not pr.getDefaults():
        defValue = pr.getDefaults().getValue(ident)
        if defValue:
            #msg += '<b>%s:</b><br>' % language.translate('help-value-default')
            #msg += valueToText(defValue.getValue())
            #msg += '<p>'

            msg += tableRow + \
                   entryHeader(language.translate('help-value-default')) + \
                   entryContent(valueToText(defValue.getValue()))

    msg += tableEnd

    # The help text of this setting.
    helpId = ident + '-help'
    if language.isDefined(helpId):
        msg += language.translate(helpId)

    msg += '</html>'

    # Display the setting information in the help panel.
    helpText.setText(msg)
    showLogo(False)

    # The info will be automatically updated in case it changes while
    # displayed.
    global currentSetting
    currentSetting = setting
Example #42
0
 def __getValueFromProfile(self):
     # Get the value for the setting as it has been defined
     # in the currently active profile.
     value = pr.getActive().getValue(self.widgetId)
     if value:
         self.setValue(int(value.getValue()))
Example #43
0
def handleCommand(event):
    """This is called when someone sends a command event.

    @param event An events.Command object."""

    # Figure out which addon has been currently selected in the addons
    # tree.  The action will target this addon.
    selected = ''

    if event.hasId('refresh-addon-database'):
        ao.refresh()

    elif event.hasId('install-addon'):
        tab30.installer.run()

    elif event.hasId('uninstall-addon'):
        selectedItems = addonList.getSelectedItems()

        # Only take the uninstallable addons.
        addons = filter(lambda i: ao.isUninstallable(i), selectedItems)
        if len(addons) == 0:
            return

        # Make sure the user wants to uninstall.
        dialog, area = sb.util.dialog.createButtonDialog(
            'uninstall-addon-dialog', ['no', 'yes'], 'no', resizable=False)

        if len(addons) == 1:
            text = language.translate('uninstall-addon-query')
            area.setExpanding(True)
            area.createRichText(
                language.expand(text, language.translate(addons[0])))
        else:
            area.setWeight(0)
            area.createText('uninstall-addon-query-several')
            msg = '<html><ul>'
            for addon in addons:
                msg += '<li>' + language.translate(addon) + '</li>'
            msg += '</ul></html>'
            ft = area.createFormattedText()
            ft.setText(msg)
            ft.setMinSize(400, 150)

        if dialog.run() == 'yes':
            for addon in addons:
                ao.uninstall(addon)
            ao.refresh()

    elif event.hasId('addon-info'):
        sel = addonList.getSelectedItems()
        if len(sel) > 0:
            # Show the Addon Inspector.
            tab30.inspector.run(ao.get(sel[0]))

    elif event.hasId('addon-settings'):
        sel = addonList.getSelectedItems()
        if len(sel) > 0:
            command = events.Command('show-addon-settings')
            command.addon = sel[0]
            events.send(command)

    elif event.hasId('load-order'):
        # Open the Load Order dialog.
        tab30.loadorder.run(pr.getActive())

    elif event.hasId('addon-list-check-selected'):
        for addon in addonList.getSelectedItems():
            pr.getActive().useAddon(addon)

    elif event.hasId('addon-list-uncheck-selected'):
        for addon in addonList.getSelectedItems():
            pr.getActive().dontUseAddon(addon)

    elif event.hasId('addon-list-check-all'):
        for addon in addonList.getItems():
            pr.getActive().useAddon(addon)

    elif event.hasId('addon-list-uncheck-all'):
        for addon in addonList.getItems():
            pr.getActive().dontUseAddon(addon)

    elif event.hasId('addon-show-parent-box'):
        for addon in addonList.getSelectedItems():
            a = ao.get(addon)
            if a.getBox():
                showInAddonList(a.getBox().getId())
            break

    elif event.hasId('addon-show-box-category'):
        for addon in addonList.getSelectedItems():
            a = ao.get(addon)
            if a.getType() == 'addon-type-box':
                addonList.deselectAllItems()
                tree.selectItem(a.getContentCategoryLongId())
                refreshListIfVisible()
            break
Example #44
0
def commandHandler(event):
    """This is called when a Command event is broadcasted."""

    global profileListDisabled

    if event.hasId("freeze"):
        profileListDisabled = True

    elif event.hasId("unfreeze"):
        profileListDisabled = False
        # notifyHandler(events.Notify('active-profile-changed'))
        pr.refresh()

    elif event.hasId("new-profile"):
        dialog, area = sb.util.dialog.createButtonDialog("new-profile-dialog", ["cancel", "ok"], "ok", resizable=False)
        dialog.disableWidget("ok")

        entry = area.createArea(alignment=ALIGN_HORIZONTAL)
        entry.setExpanding(False)

        # The name of the profile.
        entry.setWeight(1)
        entry.setBorder(4, ui.BORDER_RIGHT)
        entry.createText("new-profile-name", ":", align=wt.Text.RIGHT)
        entry.setBorder(0)
        entry.setWeight(2)
        nameField = entry.createTextField("")
        nameField.focus()

        # Only enable the OK button if there is something in the name field.
        def buttonEnabler():
            dialog.enableWidget("ok", len(nameField.getText()) > 0)

        nameField.addReaction(buttonEnabler)

        # The game component.
        entry = area.createArea(alignment=ALIGN_HORIZONTAL)
        entry.setExpanding(False)

        entry.setWeight(1)
        entry.setBorder(4, ui.BORDER_RIGHT)
        entry.createText("new-profile-game", ":", align=wt.Text.RIGHT)
        entry.setBorder(0)
        entry.setWeight(2)
        gameDrop = entry.createDropList("")

        for game in st.getGameComponents():
            gameDrop.addItem(game.getId())

        gameDrop.sortItems()

        # Select the first one.
        gameDrop.selectItem(gameDrop.getItems()[0])

        if dialog.run() == "ok":
            # Get the values from the controls.
            pr.create(nameField.getText(), gameDrop.getSelectedItem())

    elif event.hasId("rename-profile"):
        dialog, area = sb.util.dialog.createButtonDialog(
            "rename-profile-dialog", ["cancel", "ok"], "ok", resizable=False
        )

        prof = pr.getActive()

        # A text field of the new name.
        entry = area.createArea(alignment=ALIGN_HORIZONTAL)
        entry.setExpanding(False)

        # The name of the profile.
        entry.setWeight(1)
        entry.setBorder(4, ui.BORDER_RIGHT)
        entry.createText("rename-profile-name", ":", align=wt.Text.RIGHT)
        entry.setBorder(0)
        entry.setWeight(2)
        nameField = entry.createTextField("")
        nameField.setText(prof.getName())
        nameField.focus()

        # Only enable the OK button if there is something in the name
        # field.
        def buttonEnabler():
            dialog.enableWidget("ok", len(nameField.getText()) > 0)

        nameField.addReaction(buttonEnabler)

        if dialog.run() == "ok":
            prof.setName(nameField.getText())
            # The profile list needs to be updated, too.
            events.send(events.ProfileNotify(prof))
            pr.refresh()

    elif event.hasId("reset-profile"):
        dialog, area = sb.util.dialog.createButtonDialog(
            "reset-profile-dialog",
            ["cancel", "reset-profile-values", "reset-profile-addons", "reset-profile-everything"],
            "cancel",
            resizable=False,
        )

        text = language.translate("reset-profile-query")
        message = area.createRichText(language.expand(text, pr.getActive().getName()))

        # Accept these as dialog-closing commands.
        dialog.addEndCommand("reset-profile-values")
        dialog.addEndCommand("reset-profile-addons")
        dialog.addEndCommand("reset-profile-everything")

        result = dialog.run()
        if result == "cancel":
            return

        resetValues = True
        resetAddons = True
        if result == "reset-profile-values":
            resetAddons = False
        elif result == "reset-profile-addons":
            resetValues = False
        pr.reset(pr.getActive().getId(), resetValues, resetAddons)
        pr.refresh()

    elif event.hasId("delete-profile"):
        # If this is a system profile, just hide it.
        if pr.getActive().isSystemProfile():
            pr.hide(pr.getActive().getId())
            return

        dialog, area = sb.util.dialog.createButtonDialog("delete-profile-dialog", ["no", "yes"], "no", resizable=False)

        text = language.translate("delete-profile-query")
        area.createRichText(language.expand(text, pr.getActive().getName()))

        if dialog.run() == "yes":
            # Get the values from the controls.
            pr.remove(pr.getActive().getId())

    elif event.hasId("duplicate-profile"):
        dialog, area = sb.util.dialog.createButtonDialog(
            "duplicate-profile-dialog", ["cancel", "ok"], "ok", resizable=False
        )

        text = language.translate("duplicating-profile")
        area.setWeight(1)
        area.createRichText(language.expand(text, pr.getActive().getName()))

        area.setWeight(1)
        entry = area.createArea(alignment=ALIGN_HORIZONTAL)
        entry.setExpanding(False)

        # The name of the profile.
        entry.setWeight(1)
        entry.setBorder(4, ui.BORDER_RIGHT)
        entry.createText("new-profile-name", ":", align=wt.Text.RIGHT)
        entry.setBorder(0)
        entry.setWeight(3)
        nameField = entry.createTextField("")
        nameField.setText(pr.getActive().getName())
        nameField.focus()

        # Only enable the OK button if there is something in the name field.
        def buttonEnabler():
            dialog.enableWidget("ok", len(nameField.getText()) > 0)

        nameField.addReaction(buttonEnabler)

        if dialog.run() == "ok":
            pr.duplicate(pr.getActive().getId(), nameField.getText())

    elif event.hasId("hide-profile"):
        pr.hide(pr.getActive().getId())

    elif event.hasId("unhide-profiles"):
        # Display a dialog bog for unhiding hidden profiles.
        hiddenProfiles = pr.getProfiles(lambda p: p.isHidden())

        dialog, area = sb.util.dialog.createButtonDialog(
            "unhide-profile-dialog", ["cancel", "ok"], "ok", resizable=False
        )

        area.setWeight(0)
        area.createText("unhiding-profiles")

        area.setWeight(3)
        area.setBorder(0)
        profList = area.createList("", sb.widget.list.List.STYLE_CHECKBOX)
        profList.setMinSize(50, 150)

        def selectAll():
            # Check the entire list.
            for item in profList.getItems():
                profList.checkItem(item, True)

        def clearAll():
            # Uncheck the entire list.
            for item in profList.getItems():
                profList.checkItem(item, False)

        area.setWeight(0)
        controls = area.createArea(alignment=ALIGN_HORIZONTAL, border=2)
        controls.setWeight(0)
        button = controls.createButton("unhide-select-all", style=sb.widget.button.Button.STYLE_MINI)
        button.addReaction(selectAll)
        button.resizeToBestSize()
        button = controls.createButton("unhide-clear-all", style=sb.widget.button.Button.STYLE_MINI)
        button.addReaction(clearAll)
        button.resizeToBestSize()

        for prof in hiddenProfiles:
            profList.addItem(prof.getId())

        if dialog.run() == "ok":
            # Unhide all the selected items.
            selected = profList.getSelectedItems()
            for sel in selected:
                pr.show(sel)

            if len(selected):
                # Select the first one that was shown.
                pr.setActive(pr.get(selected[0]))
Example #45
0
def notifyHandler(event):
    "This is called when a Notify event is broadcasted."

    # We are interested in notifications that concern profiles.
    if event.hasId("quit"):
        # Save the current profile configuration.
        pr.save()

    elif event.hasId("language-changed"):
        # Just update the Defaults, because it's the only profile whose name
        # is translated.
        addListItem(pr.getDefaults())

    elif event.hasId("profile-updated"):
        # A profile has been loaded or updated.  Make sure it's in the
        # list.
        p = event.getProfile()

        # The Defaults profile should be first in the list.
        if p is pr.getDefaults():
            destIndex = 0
        else:
            # The new profile will be added to wherever the widget
            # wants to put it.
            destIndex = None

        if profileList.hasItem(p.getId()):
            # This already exists in the list.
            if p.isHidden():
                # Remove it completely.
                profileList.removeItem(p.getId())

                # Update the selected item since the active one is now
                # hidden.
                pr.setActive(pr.get(profileList.getSelectedItem()))
            else:
                # Just update the item.
                addListItem(p)

        elif not p.isHidden():
            # The item does not yet exist in the list.
            addListItem(p, toIndex=destIndex)

    elif event.hasId("active-profile-changed") and not profileListDisabled:
        # Highlight the correct profile in the list.
        profileList.selectItem(pr.getActive().getId())

        if pr.getActive() is pr.getDefaults():
            if deleteButton:
                deleteButton.disable()
            if dupeButton:
                dupeButton.disable()
            ui.disableMenuCommand("rename-profile")
            ui.disableMenuCommand("delete-profile")
            ui.disableMenuCommand("hide-profile")
            ui.disableMenuCommand("duplicate-profile")
            profileList.setPopupMenu(defaultsMenu)
        else:
            isSystem = pr.getActive().isSystemProfile()
            if deleteButton:
                deleteButton.enable(not isSystem)
            if dupeButton:
                dupeButton.enable()
            ui.enableMenuCommand("rename-profile")
            ui.enableMenuCommand("delete-profile", not isSystem)
            ui.enableMenuCommand("hide-profile")
            ui.enableMenuCommand("duplicate-profile")
            if isSystem:
                menu = systemMenu
            else:
                menu = normalMenu
            profileList.setPopupMenu(menu)

        # Update the banner image.
        if bannerImage:
            bannerImage.setImage(pr.getActive().getBanner())

    elif event.hasId("profile-list-selected"):
        # Change the currently active profile.
        p = pr.get(event.getSelection())
        pr.setActive(p)

        # Double-clicking causes a Play command.
        if event.isDoubleClick() and p is not pr.getDefaults():
            events.sendAfter(events.Command("play"))
Example #46
0
 def update(self):
     if self.iwadText:
         self.iwadText.getFromProfile(pr.getActive())
         self.iwadText.select()
Example #47
0
def refreshList():
    """Refreshes the list of addons."""
    addonList.freeze()

    # Try to keep the old selection, if there is one.
    oldSelections = addonList.getSelectedItems()

    addonList.clear()

    # Filtering parameters.
    profile = pr.getActive()
    isDefaults = profile is pr.getDefaults()
    if tree.getSelectedItem():
        filterCategory = ao.getCategory(tree.getSelectedItem())
    else:
        filterCategory = None

    # Which addons are currently attached?
    defaultAddons = pr.getDefaults().getAddons()
    if not isDefaults:
        profileAddons = pr.getActive().getAddons()
    else:
        profileAddons = None

    # Categories that will be in bold font in category-tree.
    boldCategories = []

    # Determine filtering options.
    mode = listFilter.getSelectedItem()
    onlyCompatible = False
    onlyPWAD = False
    alsoBoxes = False
    if 'compatible' in mode:
        onlyCompatible = True
    if 'pwad' in mode:
        onlyPWAD = True
    if 'with-boxes' in mode:
        alsoBoxes = True

    for addon in ao.getAddons():
        # Does this addon pass the filter?
        if not isDefaults and onlyCompatible:
            if not addon.isCompatibleWith(pr.getActive()):
                # Cannot be listed.
                continue
        if onlyPWAD and (addon.getType() != 'addon-type-wad'
                         or not addon.isPWAD()):
            continue
        # Has a category been selected?
        if filterCategory and not filterCategory.isAncestorOf(
                addon.getCategory()):
            # Not in the category.
            continue
        # Addons in boxes are not listed unless the correct category is selected.
        if not alsoBoxes and addon.getBox():
            # Addons in boxes are only visible if the selected category is a box category.
            boxCateg = addon.getBox().getContentCategoryLongId()
            if not filterCategory: continue
            if filterCategory.getLongId().find(boxCateg) != 0:
                # Not the right category.
                continue
        # Passed the filter!
        id = addon.getId()
        versionStr = ''
        icon = determineIcon(addon, profile, defaultAddons, profileAddons)

        if language.isDefined(id + '-version'):
            versionStr = language.translate(id + '-version')

        name = language.translate(id)
        if addon.getBox() and alsoBoxes:
            name += ' ' + language.translate('addon-list-in-box')

        addonList.addItemWithColumns(id, icon, name, versionStr)

    # Reselect old items.
    oldSelections.reverse()
    for sel in oldSelections:
        addonList.selectItem(sel)
        addonList.ensureVisible(sel)

    sortList()
    updateButtons()

    addonList.unfreeze()

    # Update the counter text.
    countText.setText(
        language.expand(language.translate('addon-counter'),
                        str(len(addonList.getItems())),
                        str(ao.getAddonCount())))

    # Update boldings in category-tree.
    # --TODO!--

    global mustRefreshList
    mustRefreshList = False