Example #1
0
    def __init__(self, parent, bandwidth_rules):

        ClientGUICommon.StaticBox.__init__(self, parent, 'bandwidth rules')

        listctrl_panel = ClientGUIListCtrl.BetterListCtrlPanel(self)

        columns = [('max allowed', 14), ('every', 16)]

        self._listctrl = ClientGUIListCtrl.BetterListCtrl(
            listctrl_panel,
            'bandwidth_rules',
            8,
            10,
            columns,
            self._ConvertRuleToListCtrlTuples,
            use_simple_delete=True,
            activation_callback=self._Edit)

        listctrl_panel.SetListCtrl(self._listctrl)

        listctrl_panel.AddButton('add', self._Add)
        listctrl_panel.AddButton('edit',
                                 self._Edit,
                                 enabled_only_on_selection=True)
        listctrl_panel.AddDeleteButton()

        #

        self._listctrl.AddDatas(bandwidth_rules.GetRules())

        self._listctrl.Sort(0)

        #

        self.Add(listctrl_panel, CC.FLAGS_EXPAND_BOTH_WAYS)
Example #2
0
 def __init__( self, parent, initial_dict: typing.Dict[ str, ClientParsing.StringMatch ], min_height = 10, key_name = 'key' ):
     
     QW.QWidget.__init__( self, parent )
     
     self._key_name = key_name
     
     listctrl_panel = ClientGUIListCtrl.BetterListCtrlPanel( self )
     
     columns = [ ( self._key_name, 20 ), ( 'matching', -1 ) ]
     
     self._listctrl = ClientGUIListCtrl.BetterListCtrl( listctrl_panel, 'key_to_string_match', min_height, 36, columns, self._ConvertDataToListCtrlTuples, use_simple_delete = True, activation_callback = self._Edit )
     
     listctrl_panel.SetListCtrl( self._listctrl )
     
     listctrl_panel.AddButton( 'add', self._Add )
     listctrl_panel.AddButton( 'edit', self._Edit, enabled_only_on_selection = True )
     listctrl_panel.AddDeleteButton()
     
     #
     
     self._listctrl.AddDatas( initial_dict.items() )
     
     self._listctrl.Sort( 0 )
     
     #
     
     vbox = QP.VBoxLayout()
     
     QP.AddToLayout( vbox, listctrl_panel, CC.FLAGS_EXPAND_BOTH_WAYS )
     
     self.setLayout( vbox )
Example #3
0
    def __init__(self,
                 parent,
                 favourite_searches_rows,
                 initial_search_row_to_edit=None):

        ClientGUIScrolledPanels.EditPanel.__init__(self, parent)

        self._favourite_searches_panel = ClientGUIListCtrl.BetterListCtrlPanel(
            self)

        columns = [('folder', 24), ('name', 24), ('search', -1), ('sort', 24),
                   ('collect', 24)]

        self._favourite_searches = ClientGUIListCtrl.BetterListCtrl(
            self._favourite_searches_panel,
            'favourite_searches',
            20,
            72,
            columns,
            self._ConvertRowToListCtrlTuples,
            use_simple_delete=True,
            activation_callback=self._EditFavouriteSearch)

        self._favourite_searches_panel.SetListCtrl(self._favourite_searches)

        self._favourite_searches_panel.AddButton('add',
                                                 self._AddNewFavouriteSearch)
        self._favourite_searches_panel.AddButton(
            'edit', self._EditFavouriteSearch, enabled_only_on_selection=True)
        self._favourite_searches_panel.AddDeleteButton()

        #

        self._favourite_searches.AddDatas(favourite_searches_rows)

        self._favourite_searches.Sort(0)

        #

        vbox = QP.VBoxLayout()

        QP.AddToLayout(vbox, self._favourite_searches_panel,
                       CC.FLAGS_EXPAND_BOTH_WAYS)

        self.widget().setLayout(vbox)

        if initial_search_row_to_edit is not None:

            HG.client_controller.CallLaterQtSafe(self, 0.5,
                                                 self._AddNewFavouriteSearch,
                                                 initial_search_row_to_edit)
Example #4
0
 def __init__( self, parent ):
     
     title = 'manage local upnp'
     
     ClientGUIDialogs.Dialog.__init__( self, parent, title )
     
     self._status_st = ClientGUICommon.BetterStaticText( self )
     
     listctrl_panel = ClientGUIListCtrl.BetterListCtrlPanel( self )
     
     columns = [ ( 'description', -1 ), ( 'internal ip', 17 ), ( 'internal port', 7 ), ( 'external port', 7 ), ( 'prototcol', 5 ), ( 'lease', 12 ) ]
     
     self._mappings_list_ctrl = ClientGUIListCtrl.BetterListCtrl( listctrl_panel, 'manage_upnp_mappings', 12, 36, columns, self._ConvertDataToListCtrlTuples, delete_key_callback = self._Remove, activation_callback = self._Edit )
     
     listctrl_panel.SetListCtrl( self._mappings_list_ctrl )
     
     listctrl_panel.AddButton( 'add custom mapping', self._Add )
     listctrl_panel.AddButton( 'edit mapping', self._Edit, enabled_only_on_selection = True )
     listctrl_panel.AddButton( 'remove mapping', self._Remove, enabled_only_on_selection = True )
     
     self._ok = QW.QPushButton( 'ok', self )
     self._ok.clicked.connect( self.EventOK )
     self._ok.setObjectName( 'HydrusAccept' )
     
     #
     
     vbox = QP.VBoxLayout()
     
     QP.AddToLayout( vbox, self._status_st, CC.FLAGS_EXPAND_PERPENDICULAR )
     QP.AddToLayout( vbox, listctrl_panel, CC.FLAGS_EXPAND_BOTH_WAYS )
     QP.AddToLayout( vbox, self._ok, CC.FLAGS_LONE_BUTTON )
     
     self.setLayout( vbox )
     
     size_hint = self.sizeHint()
     
     size_hint.setWidth( max( size_hint.width(), 760 ) )
     
     QP.SetInitialSize( self, size_hint )
     
     #
     
     self._mappings = []
     
     self._mappings_list_ctrl.Sort( 0 )
     
     self._started_external_ip_fetch = False
     
     self._RefreshMappings()
Example #5
0
 def __init__( self, parent, initial_dict: typing.Dict[ str, str ], min_height = 10, key_name = 'key', value_name = 'value', allow_add_delete = True, edit_keys = True ):
     
     QW.QWidget.__init__( self, parent )
     
     self._key_name = key_name
     self._value_name = value_name
     
     self._edit_keys = edit_keys
     
     listctrl_panel = ClientGUIListCtrl.BetterListCtrlPanel( self )
     
     columns = [ ( self._key_name, 20 ), ( self._value_name, -1 ) ]
     
     use_simple_delete = allow_add_delete
     
     self._listctrl = ClientGUIListCtrl.BetterListCtrl( listctrl_panel, 'key_to_value', min_height, 36, columns, self._ConvertDataToListCtrlTuples, use_simple_delete = use_simple_delete, activation_callback = self._Edit )
     self._listctrl.listCtrlChanged.connect( self.listCtrlChanged )
     
     listctrl_panel.SetListCtrl( self._listctrl )
     
     if allow_add_delete:
         
         listctrl_panel.AddButton( 'add', self._Add )
         
     
     listctrl_panel.AddButton( 'edit', self._Edit, enabled_only_on_selection = True )
     
     if allow_add_delete:
         
         listctrl_panel.AddDeleteButton()
         
     
     #
     
     self._listctrl.AddDatas( list(initial_dict.items()) )
     
     self._listctrl.Sort( 0 )
     
     #
     
     vbox = QP.VBoxLayout()
     
     QP.AddToLayout( vbox, listctrl_panel, CC.FLAGS_EXPAND_BOTH_WAYS )
     
     self.setLayout( vbox )
    def __init__(self, parent, export_folders):

        ClientGUIScrolledPanels.EditPanel.__init__(self, parent)

        self._export_folders_panel = ClientGUIListCtrl.BetterListCtrlPanel(
            self)

        columns = [('name', 20), ('path', -1), ('type', 12), ('query', 16),
                   ('paused', 8), ('period', 16), ('phrase', 20)]

        self._export_folders = ClientGUIListCtrl.BetterListCtrl(
            self._export_folders_panel,
            'export_folders',
            6,
            40,
            columns,
            self._ConvertExportFolderToListCtrlTuples,
            use_simple_delete=True,
            activation_callback=self._Edit)

        self._export_folders_panel.SetListCtrl(self._export_folders)

        self._export_folders_panel.AddButton('add', self._AddFolder)
        self._export_folders_panel.AddButton('edit',
                                             self._Edit,
                                             enabled_only_on_selection=True)
        self._export_folders_panel.AddDeleteButton()

        #

        self._export_folders.AddDatas(export_folders)

        self._export_folders.Sort(0)

        vbox = QP.VBoxLayout()

        intro = 'Here you can set the client to regularly export a certain query to a particular location.'

        QP.AddToLayout(vbox, ClientGUICommon.BetterStaticText(self, intro),
                       CC.FLAGS_EXPAND_PERPENDICULAR)
        QP.AddToLayout(vbox, self._export_folders_panel,
                       CC.FLAGS_EXPAND_BOTH_WAYS)

        self.widget().setLayout(vbox)
Example #7
0
    def _ConvertFileSeedToListCtrlTuples(self, file_seed):

        try:

            file_seed_index = self._file_seed_cache.GetFileSeedIndex(file_seed)

            pretty_file_seed_index = HydrusData.ToHumanInt(file_seed_index)

        except:

            file_seed_index = '--'

            pretty_file_seed_index = '--'

        file_seed_data = file_seed.file_seed_data
        status = file_seed.status
        added = file_seed.created
        modified = file_seed.modified
        source_time = file_seed.source_time
        note = file_seed.note

        pretty_file_seed_data = str(file_seed_data)
        pretty_status = CC.status_string_lookup[status]
        pretty_added = HydrusData.TimestampToPrettyTimeDelta(added)
        pretty_modified = HydrusData.TimestampToPrettyTimeDelta(modified)

        if source_time is None:

            pretty_source_time = 'unknown'

        else:

            pretty_source_time = HydrusData.TimestampToPrettyTimeDelta(
                source_time)

        sort_source_time = ClientGUIListCtrl.SafeNoneInt(source_time)

        pretty_note = note.split(os.linesep)[0]

        display_tuple = (pretty_file_seed_index, pretty_file_seed_data,
                         pretty_status, pretty_added, pretty_modified,
                         pretty_source_time, pretty_note)
        sort_tuple = (file_seed_index, file_seed_data, status, added, modified,
                      sort_source_time, note)

        return (display_tuple, sort_tuple)
Example #8
0
    def __init__(self, parent, controller, file_seed_cache):

        ClientGUIScrolledPanels.EditPanel.__init__(self, parent)

        self._controller = controller
        self._file_seed_cache = file_seed_cache

        self._text = ClientGUICommon.BetterStaticText(self, 'initialising')

        # add index control row here, hide it if needed and hook into showing/hiding and postsizechangedevent on file_seed add/remove

        columns = [('#', 3), ('source', -1), ('status', 12), ('added', 23),
                   ('last modified', 23), ('source time', 23), ('note', 20)]

        self._list_ctrl = ClientGUIListCtrl.BetterListCtrl(
            self,
            'file_seed_cache',
            30,
            30,
            columns,
            self._ConvertFileSeedToListCtrlTuples,
            activation_callback=self._ShowSelectionInNewPage,
            delete_key_callback=self._DeleteSelected)

        #

        self._list_ctrl.AddDatas(self._file_seed_cache.GetFileSeeds())

        self._list_ctrl.Sort(0)

        #

        vbox = QP.VBoxLayout()

        QP.AddToLayout(vbox, self._text, CC.FLAGS_EXPAND_PERPENDICULAR)
        QP.AddToLayout(vbox, self._list_ctrl, CC.FLAGS_EXPAND_BOTH_WAYS)

        self.widget().setLayout(vbox)

        self._list_ctrl.AddMenuCallable(self._GetListCtrlMenu)

        self._controller.sub(self, 'NotifyFileSeedsUpdated',
                             'file_seed_cache_file_seeds_updated')

        QP.CallAfter(self._UpdateText)
Example #9
0
    def _ConvertRuleToListCtrlTuples(self, rule):

        (bandwidth_type, time_delta, max_allowed) = rule

        pretty_time_delta = HydrusData.TimeDeltaToPrettyTimeDelta(time_delta)

        if bandwidth_type == HC.BANDWIDTH_TYPE_DATA:

            pretty_max_allowed = HydrusData.ToHumanBytes(max_allowed)

        elif bandwidth_type == HC.BANDWIDTH_TYPE_REQUESTS:

            pretty_max_allowed = HydrusData.ToHumanInt(
                max_allowed) + ' requests'

        sort_time_delta = ClientGUIListCtrl.SafeNoneInt(time_delta)

        sort_tuple = (max_allowed, sort_time_delta)
        display_tuple = (pretty_max_allowed, pretty_time_delta)

        return (display_tuple, sort_tuple)
Example #10
0
 def __init__( self, parent, controller, read_only, can_generate_more_pages, gallery_seed_log ):
     
     ClientGUIScrolledPanels.EditPanel.__init__( self, parent )
     
     self._controller = controller
     self._read_only = read_only
     self._can_generate_more_pages = can_generate_more_pages
     self._gallery_seed_log = gallery_seed_log
     
     self._text = ClientGUICommon.BetterStaticText( self, 'initialising' )
     
     # add index control row here, hide it if needed and hook into showing/hiding and postsizechangedevent on gallery_seed add/remove
     
     columns = [ ( '#', 3 ), ( 'url', -1 ), ( 'status', 12 ), ( 'added', 23 ), ( 'last modified', 23 ), ( 'note', 20 ) ]
     
     self._list_ctrl = ClientGUIListCtrl.BetterListCtrl( self, 'gallery_seed_log', 30, 30, columns, self._ConvertGallerySeedToListCtrlTuples )
     
     #
     
     self._list_ctrl.AddDatas( self._gallery_seed_log.GetGallerySeeds() )
     
     self._list_ctrl.Sort( 0 )
     
     #
     
     vbox = QP.VBoxLayout()
     
     QP.AddToLayout( vbox, self._text, CC.FLAGS_EXPAND_PERPENDICULAR )
     QP.AddToLayout( vbox, self._list_ctrl, CC.FLAGS_EXPAND_BOTH_WAYS )
     
     self.widget().setLayout( vbox )
     
     self._list_ctrl.AddMenuCallable( self._GetListCtrlMenu )
     
     self._controller.sub( self, 'NotifyGallerySeedsUpdated', 'gallery_seed_log_gallery_seeds_updated' )
     
     QP.CallAfter( self._UpdateText )
Example #11
0
    def __init__(self, parent, all_shortcuts):

        ClientGUIScrolledPanels.EditPanel.__init__(self, parent)

        help_button = ClientGUICommon.BetterBitmapButton(
            self,
            CC.global_pixmaps().help, self._ShowHelp)
        help_button.setToolTip('Show help regarding editing shortcuts.')

        reserved_panel = ClientGUICommon.StaticBox(
            self, 'built-in hydrus shortcut sets')

        self._reserved_shortcuts = ClientGUIListCtrl.BetterListCtrl(
            reserved_panel,
            'reserved_shortcuts',
            6,
            30, [('name', -1), ('number of shortcuts', 20)],
            data_to_tuples_func=self._GetTuples,
            activation_callback=self._EditReserved)

        self._reserved_shortcuts.setMinimumSize(QC.QSize(320, 200))

        self._edit_reserved_button = ClientGUICommon.BetterButton(
            reserved_panel, 'edit', self._EditReserved)
        self._restore_defaults_button = ClientGUICommon.BetterButton(
            reserved_panel, 'restore defaults', self._RestoreDefaults)

        #

        custom_panel = ClientGUICommon.StaticBox(self, 'custom user sets')

        self._custom_shortcuts = ClientGUIListCtrl.BetterListCtrl(
            custom_panel,
            'custom_shortcuts',
            6,
            30, [('name', -1), ('number of shortcuts', 20)],
            data_to_tuples_func=self._GetTuples,
            delete_key_callback=self._Delete,
            activation_callback=self._EditCustom)

        self._add_button = ClientGUICommon.BetterButton(
            custom_panel, 'add', self._Add)
        self._edit_custom_button = ClientGUICommon.BetterButton(
            custom_panel, 'edit', self._EditCustom)
        self._delete_button = ClientGUICommon.BetterButton(
            custom_panel, 'delete', self._Delete)

        if not HG.client_controller.new_options.GetBoolean('advanced_mode'):

            custom_panel.hide()

        #

        reserved_shortcuts = [
            shortcuts for shortcuts in all_shortcuts if shortcuts.GetName() in
            ClientGUIShortcuts.SHORTCUTS_RESERVED_NAMES
        ]
        custom_shortcuts = [
            shortcuts for shortcuts in all_shortcuts if shortcuts.GetName()
            not in ClientGUIShortcuts.SHORTCUTS_RESERVED_NAMES
        ]

        self._reserved_shortcuts.AddDatas(reserved_shortcuts)

        self._reserved_shortcuts.Sort(0)

        self._original_custom_names = set()

        for shortcuts in custom_shortcuts:

            self._custom_shortcuts.AddDatas((shortcuts, ))

            self._original_custom_names.add(shortcuts.GetName())

        self._custom_shortcuts.Sort(0)

        #

        button_hbox = QP.HBoxLayout()

        QP.AddToLayout(button_hbox, self._edit_reserved_button,
                       CC.FLAGS_VCENTER)
        QP.AddToLayout(button_hbox, self._restore_defaults_button,
                       CC.FLAGS_VCENTER)

        reserved_panel.Add(self._reserved_shortcuts,
                           CC.FLAGS_EXPAND_SIZER_BOTH_WAYS)
        reserved_panel.Add(button_hbox, CC.FLAGS_BUTTON_SIZER)

        #

        button_hbox = QP.HBoxLayout()

        QP.AddToLayout(button_hbox, self._add_button, CC.FLAGS_VCENTER)
        QP.AddToLayout(button_hbox, self._edit_custom_button, CC.FLAGS_VCENTER)
        QP.AddToLayout(button_hbox, self._delete_button, CC.FLAGS_VCENTER)

        custom_panel_message = 'Custom shortcuts are advanced. They apply to the media viewer and must be turned on to take effect.'

        st = ClientGUICommon.BetterStaticText(custom_panel,
                                              custom_panel_message)
        st.setWordWrap(True)

        custom_panel.Add(st, CC.FLAGS_EXPAND_PERPENDICULAR)
        custom_panel.Add(self._custom_shortcuts,
                         CC.FLAGS_EXPAND_SIZER_BOTH_WAYS)
        custom_panel.Add(button_hbox, CC.FLAGS_BUTTON_SIZER)

        #

        vbox = QP.VBoxLayout()

        QP.AddToLayout(vbox, help_button, CC.FLAGS_LONE_BUTTON)
        QP.AddToLayout(vbox, reserved_panel, CC.FLAGS_EXPAND_BOTH_WAYS)
        QP.AddToLayout(vbox, custom_panel, CC.FLAGS_EXPAND_BOTH_WAYS)

        self.widget().setLayout(vbox)
Example #12
0
    def __init__(self, parent, shortcuts: ClientGUIShortcuts.ShortcutSet):

        ClientGUIScrolledPanels.EditPanel.__init__(self, parent)

        self._name = QW.QLineEdit(self)

        self._shortcuts_panel = ClientGUIListCtrl.BetterListCtrlPanel(self)

        self._shortcuts = ClientGUIListCtrl.BetterListCtrl(
            self._shortcuts_panel,
            'shortcuts',
            20,
            20, [('shortcut', 20), ('command', -1)],
            data_to_tuples_func=self._ConvertSortTupleToPrettyTuple,
            delete_key_callback=self.RemoveShortcuts,
            activation_callback=self.EditShortcuts)

        self._shortcuts_panel.SetListCtrl(self._shortcuts)

        self._shortcuts_panel.AddImportExportButtons(
            (ClientGUIShortcuts.ShortcutSet, ),
            self._AddShortcutSet,
            custom_get_callable=self._GetSelectedShortcutSet)

        self._shortcuts.setMinimumSize(QC.QSize(360, 480))

        self._add = QW.QPushButton('add', self)
        self._add.clicked.connect(self.AddShortcut)

        self._edit = QW.QPushButton('edit', self)
        self._edit.clicked.connect(self.EditShortcuts)

        self._remove = QW.QPushButton('remove', self)
        self._remove.clicked.connect(self.RemoveShortcuts)

        #

        name = shortcuts.GetName()

        self._name.setText(name)

        self._this_is_custom = True

        if name in ClientGUIShortcuts.SHORTCUTS_RESERVED_NAMES:

            self._this_is_custom = False

            self._name.setEnabled(False)

        self._shortcuts.AddDatas(shortcuts)

        self._shortcuts.Sort(1)

        #

        action_buttons = QP.HBoxLayout()

        QP.AddToLayout(action_buttons, self._add, CC.FLAGS_VCENTER)
        QP.AddToLayout(action_buttons, self._edit, CC.FLAGS_VCENTER)
        QP.AddToLayout(action_buttons, self._remove, CC.FLAGS_VCENTER)

        vbox = QP.VBoxLayout()

        QP.AddToLayout(vbox,
                       ClientGUICommon.WrapInText(self._name, self, 'name: '),
                       CC.FLAGS_EXPAND_SIZER_PERPENDICULAR)

        if name in ClientGUIShortcuts.shortcut_names_to_descriptions:

            description_text = ClientGUIShortcuts.shortcut_names_to_descriptions[
                name]

            description = ClientGUICommon.BetterStaticText(
                self, description_text, description_text)

            description.setWordWrap(True)

            QP.AddToLayout(vbox, description, CC.FLAGS_EXPAND_PERPENDICULAR)

        QP.AddToLayout(vbox, self._shortcuts_panel, CC.FLAGS_EXPAND_BOTH_WAYS)
        QP.AddToLayout(vbox, action_buttons, CC.FLAGS_BUTTON_SIZER)

        self.widget().setLayout(vbox)
Example #13
0
    def __init__(self, parent, flat_media, do_export_and_then_quit=False):

        ClientGUIScrolledPanels.ReviewPanel.__init__(self, parent)

        new_options = HG.client_controller.new_options

        self._media_to_paths = {}
        self._existing_filenames = set()
        self._last_phrase_used = ''
        self._last_dir_used = ''

        self._tags_box = ClientGUIListBoxes.StaticBoxSorterForListBoxTags(
            self, 'files\' tags')

        services_manager = HG.client_controller.services_manager

        self._neighbouring_txt_tag_service_keys = services_manager.FilterValidServiceKeys(
            new_options.GetKeyList(
                'default_neighbouring_txt_tag_service_keys'))

        t = ClientGUIListBoxes.ListBoxTagsMedia(
            self._tags_box,
            ClientTags.TAG_DISPLAY_SIBLINGS_AND_PARENTS,
            include_counts=True)

        self._tags_box.SetTagsBox(t)

        self._tags_box.setMinimumSize(QC.QSize(220, 300))

        columns = [('number', 8), ('filetype', 20), ('expected path', -1)]

        self._paths = ClientGUIListCtrl.BetterListCtrl(
            self,
            'export_files',
            24,
            64,
            columns,
            self._ConvertDataToListCtrlTuples,
            use_simple_delete=True)

        self._paths.Sort(0)

        self._export_path_box = ClientGUICommon.StaticBox(self, 'export path')

        self._directory_picker = QP.DirPickerCtrl(self._export_path_box)
        self._directory_picker.dirPickerChanged.connect(self._RefreshPaths)

        self._open_location = QW.QPushButton('open this location',
                                             self._export_path_box)
        self._open_location.clicked.connect(self.EventOpenLocation)

        self._filenames_box = ClientGUICommon.StaticBox(self, 'filenames')

        self._pattern = QW.QLineEdit(self._filenames_box)

        self._update = QW.QPushButton('update', self._filenames_box)
        self._update.clicked.connect(self._RefreshPaths)

        self._examples = ClientGUICommon.ExportPatternButton(
            self._filenames_box)

        self._delete_files_after_export = QW.QCheckBox(
            'delete files from client after export?', self)
        self._delete_files_after_export.setObjectName('HydrusWarning')

        self._export_symlinks = QW.QCheckBox('EXPERIMENTAL: export symlinks',
                                             self)
        self._export_symlinks.setObjectName('HydrusWarning')

        text = 'This will export all the files\' tags, newline separated, into .txts beside the files themselves.'

        self._export_tag_txts_services_button = ClientGUICommon.BetterButton(
            self, 'set .txt services', self._SetTxtServices)

        self._export_tag_txts = QW.QCheckBox('export tags to .txt files?',
                                             self)
        self._export_tag_txts.setToolTip(text)
        self._export_tag_txts.clicked.connect(self.EventExportTagTxtsChanged)

        self._export = QW.QPushButton('export', self)
        self._export.clicked.connect(self._DoExport)

        #

        export_path = ClientExporting.GetExportPath()

        self._directory_picker.SetPath(export_path)

        phrase = new_options.GetString('export_phrase')

        self._pattern.setText(phrase)

        if len(self._neighbouring_txt_tag_service_keys) > 0:

            self._export_tag_txts.setChecked(True)

        self._paths.SetData(list(enumerate(flat_media)))

        self._delete_files_after_export.setChecked(
            HG.client_controller.new_options.GetBoolean(
                'delete_files_after_export'))
        self._delete_files_after_export.clicked.connect(
            self.EventDeleteFilesChanged)

        if not HG.client_controller.new_options.GetBoolean('advanced_mode'):

            self._export_symlinks.setVisible(False)

        #

        top_hbox = QP.HBoxLayout()

        QP.AddToLayout(top_hbox, self._tags_box, CC.FLAGS_EXPAND_PERPENDICULAR)
        QP.AddToLayout(top_hbox, self._paths, CC.FLAGS_EXPAND_BOTH_WAYS)

        hbox = QP.HBoxLayout()

        QP.AddToLayout(hbox, self._directory_picker, CC.FLAGS_EXPAND_BOTH_WAYS)
        QP.AddToLayout(hbox, self._open_location, CC.FLAGS_VCENTER)

        self._export_path_box.Add(hbox, CC.FLAGS_EXPAND_SIZER_PERPENDICULAR)

        hbox = QP.HBoxLayout()

        QP.AddToLayout(hbox, self._pattern, CC.FLAGS_EXPAND_BOTH_WAYS)
        QP.AddToLayout(hbox, self._update, CC.FLAGS_VCENTER)
        QP.AddToLayout(hbox, self._examples, CC.FLAGS_VCENTER)

        self._filenames_box.Add(hbox, CC.FLAGS_EXPAND_SIZER_PERPENDICULAR)

        txt_hbox = QP.HBoxLayout()

        QP.AddToLayout(txt_hbox, self._export_tag_txts_services_button,
                       CC.FLAGS_VCENTER)
        QP.AddToLayout(txt_hbox, self._export_tag_txts, CC.FLAGS_VCENTER)

        vbox = QP.VBoxLayout()

        QP.AddToLayout(vbox, top_hbox, CC.FLAGS_EXPAND_SIZER_BOTH_WAYS)
        QP.AddToLayout(vbox, self._export_path_box,
                       CC.FLAGS_EXPAND_PERPENDICULAR)
        QP.AddToLayout(vbox, self._filenames_box,
                       CC.FLAGS_EXPAND_PERPENDICULAR)
        QP.AddToLayout(vbox, self._delete_files_after_export,
                       CC.FLAGS_LONE_BUTTON)
        QP.AddToLayout(vbox, self._export_symlinks, CC.FLAGS_LONE_BUTTON)
        QP.AddToLayout(vbox, txt_hbox, CC.FLAGS_LONE_BUTTON)
        QP.AddToLayout(vbox, self._export, CC.FLAGS_LONE_BUTTON)

        self.widget().setLayout(vbox)

        self._RefreshTags()

        self._UpdateTxtButton()

        HG.client_controller.CallAfterQtSafe(self._export,
                                             self._export.setFocus,
                                             QC.Qt.OtherFocusReason)

        self._paths.itemSelectionChanged.connect(self._RefreshTags)

        if do_export_and_then_quit:

            QP.CallAfter(self._DoExport, True)