 mythtv/libs/libmythbase/libmythbase.pro            |  3 ++
 mythtv/libs/libmythbase/mythsorthelper.cpp         | 47 +++++++++++++++++++
 mythtv/libs/libmythbase/mythsorthelper.h           | 30 +++++++++++++
 mythtv/libs/libmythmetadata/videometadata.cpp      | 27 ++---------
 mythtv/libs/libmythmetadata/videometadata.h        |  4 +-
 mythtv/programs/mythfrontend/globalsettings.cpp    | 38 ++++++++++++++++
 mythtv/programs/mythfrontend/playbackbox.cpp       |  9 ++--
 mythtv/programs/mythfrontend/playbackbox.h         |  3 +-
 mythtv/programs/mythfrontend/proglist.cpp          | 10 +++--
 mythtv/programs/mythfrontend/proglist.h            |  3 ++
 .../programs/mythfrontend/programrecpriority.cpp   |  5 +--
 mythtv/programs/mythfrontend/programrecpriority.h  |  2 +
 mythtv/programs/mythfrontend/videofilter.cpp       | 19 ++++----
 mythtv/programs/mythfrontend/videofilter.h         |  7 +--
 mythtv/programs/mythfrontend/videolist.cpp         | 52 ++++++++--------------
 15 files changed, 174 insertions(+), 85 deletions(-)

diff --git a/mythtv/libs/libmythbase/libmythbase.pro b/mythtv/libs/libmythbase/libmythbase.pro
index 228617a..286f909 100644
--- a/mythtv/libs/libmythbase/libmythbase.pro
+++ b/mythtv/libs/libmythbase/libmythbase.pro
@@ -34,6 +34,7 @@ HEADERS += threadedfilewriter.h mythsingledownload.h codecutil.h
 HEADERS += mythsession.h
 HEADERS += ../../external/qjsonwrapper/qjsonwrapper/Json.h
 HEADERS += cleanupguard.h
+HEADERS += mythsorthelper.h
 
 SOURCES += mthread.cpp mthreadpool.cpp
 SOURCES += mythsocket.cpp
@@ -55,6 +56,7 @@ SOURCES += threadedfilewriter.cpp mythsingledownload.cpp codecutil.cpp
 SOURCES += mythsession.cpp
 SOURCES += ../../external/qjsonwrapper/qjsonwrapper/Json.cpp
 SOURCES += cleanupguard.cpp
+SOURCES += mythsorthelper.cpp
 
 unix {
     SOURCES += mythsystemunix.cpp
@@ -84,6 +86,7 @@ inc.files += plist.h bswap.h signalhandling.h ffmpeg-mmx.h mythdate.h
 inc.files += mythplugin.h mythpluginapi.h mythqtcompat.h
 inc.files += remotefile.h mythsystemlegacy.h mythtypes.h
 inc.files += threadedfilewriter.h mythsingledownload.h mythsession.h
+inc.files += mythsorthelper.h
 
 # Allow both #include <blah.h> and #include <libmythbase/blah.h>
 inc2.path  = $${PREFIX}/include/mythtv/libmythbase
diff --git a/mythtv/libs/libmythbase/mythsorthelper.cpp b/mythtv/libs/libmythbase/mythsorthelper.cpp
new file mode 100644
index 0000000..9f1de4b
--- /dev/null
+++ b/mythtv/libs/libmythbase/mythsorthelper.cpp
@@ -0,0 +1,47 @@
+// -*- Mode: c++ -*-
+// vim: set expandtab tabstop=4 shiftwidth=4
+
+#include "mythsorthelper.h"
+#include "mythcorecontext.h"
+
+SortHelper::SortHelper()
+{
+    QString prefixes(tr("^(The |A |An )",
+			"Regular Expression for what to ignore when sorting"));
+    m_ignore_case = gCoreContext->GetNumSetting("SortIgnoreCase", true);
+    m_ignore_prefixes = gCoreContext->GetNumSetting("SortIgnorePrefixes", true);
+    QString excludes = gCoreContext->GetSetting("SortIgnorePrefixExceptions", "");
+    if (m_ignore_case)
+    {
+        prefixes = prefixes.toLower();
+        excludes = excludes.toLower();
+    }
+    m_ign_regex1 = QRegExp(prefixes);
+    m_ign_regex2 = QRegExp(prefixes.replace("^","/"));
+    m_excl_list = excludes.split(";", QString::SkipEmptyParts);
+    for (int i = 0; i < m_excl_list.size(); i++)
+      m_excl_list[i] = m_excl_list[i].trimmed();
+    m_creator = "unknown";
+}
+
+QString SortHelper::doTitle(QString title) const
+{
+    if (m_ignore_case)
+        title = title.toLower();
+    if (not m_ignore_prefixes)
+	return title;
+    if (m_excl_list.contains(title))
+	return title;
+    return title.remove(m_ign_regex1);
+}
+
+QString SortHelper::doFilename(QString filename) const
+{
+    if (m_ignore_case)
+        filename = filename.toLower();
+    if (not m_ignore_prefixes)
+	return filename;
+    if (m_excl_list.contains(filename))
+	return filename;
+    return filename.remove(m_ign_regex1).replace(m_ign_regex2, "/");
+}
diff --git a/mythtv/libs/libmythbase/mythsorthelper.h b/mythtv/libs/libmythbase/mythsorthelper.h
new file mode 100644
index 0000000..d2697d7
--- /dev/null
+++ b/mythtv/libs/libmythbase/mythsorthelper.h
@@ -0,0 +1,30 @@
+// -*- Mode: c++ -*-
+// vim: set expandtab tabstop=4 shiftwidth=4
+
+#ifndef MYTHSORTHELPER_H_
+#define MYTHSORTHELPER_H_
+
+#include <QCoreApplication>
+#include "mythbaseexp.h"
+
+class MBASE_PUBLIC SortHelper
+{
+    Q_DECLARE_TR_FUNCTIONS(SortHelper)
+
+  public:
+    SortHelper();
+    QString doTitle(QString title) const;
+    QString doFilename(QString filename) const;
+
+  private:
+    bool m_ignore_case;
+
+    bool m_ignore_prefixes;
+    QRegExp m_ign_regex1;	// Anchored at the start
+    QRegExp m_ign_regex2;	// Following a '/'
+
+    QStringList m_excl_list;
+    QString m_creator;
+};
+
+#endif // MYTHSORTHELPER_H_
diff --git a/mythtv/libs/libmythmetadata/videometadata.cpp b/mythtv/libs/libmythmetadata/videometadata.cpp
index 8f4c2b4..9021e55 100644
--- a/mythtv/libs/libmythmetadata/videometadata.cpp
+++ b/mythtv/libs/libmythmetadata/videometadata.cpp
@@ -961,12 +961,11 @@ void VideoMetadataImp::GetImageMap(InfoMap &imageMap) const
 //// Metadata
 ////////////////////////////////////////
 VideoMetadata::SortKey VideoMetadata::GenerateDefaultSortKey(const VideoMetadata &m,
-                                                   bool ignore_case)
+                                                   const SortHelper &sort_helper)
 {
-    QString title(ignore_case ? m.GetTitle().toLower() : m.GetTitle());
-    title = TrimTitle(title, ignore_case);
-
-    return SortKey(SortData(title, m.GetFilename(),
+    QString title = sort_helper.doTitle(m.GetTitle());
+    QString filename = sort_helper.doFilename(m.GetFilename());
+    return SortKey(SortData(title, filename,
                          QString().sprintf("%.7d", m.GetID())));
 }
 
@@ -1172,24 +1171,6 @@ QString VideoMetadata::FilenameToMeta(const QString &file_name, int position)
     return QString();
 }
 
-namespace
-{
-    const QRegExp &getTitleTrim(bool ignore_case)
-    {
-        static QString pattern(VideoMetadata::tr("^(The |A |An )"));
-        static QRegExp prefixes_case(pattern, Qt::CaseSensitive);
-        static QRegExp prefixes_nocase(pattern, Qt::CaseInsensitive);
-        return ignore_case ? prefixes_nocase : prefixes_case;
-    }
-}
-
-QString VideoMetadata::TrimTitle(const QString &title, bool ignore_case)
-{
-    QString ret(title);
-    ret.remove(getTitleTrim(ignore_case));
-    return ret;
-}
-
 VideoMetadata::VideoMetadata(const QString &filename, const QString &hash,
              const QString &trailer, const QString &coverfile,
              const QString &screenshot, const QString &banner, const QString &fanart,
diff --git a/mythtv/libs/libmythmetadata/videometadata.h b/mythtv/libs/libmythmetadata/videometadata.h
index a02587c..3587576 100644
--- a/mythtv/libs/libmythmetadata/videometadata.h
+++ b/mythtv/libs/libmythmetadata/videometadata.h
@@ -11,6 +11,7 @@
 #include "parentalcontrols.h"
 #include "mythmetaexp.h"
 #include "metadatacommon.h"
+#include "mythsorthelper.h"
 
 class MSqlQuery;
 class VideoMetadataListManager;
@@ -53,7 +54,8 @@ class META_PUBLIC VideoMetadata
     };
 
   public:
-    static SortKey GenerateDefaultSortKey(const VideoMetadata &m, bool ignore_case);
+    static SortKey GenerateDefaultSortKey(const VideoMetadata &m,
+					  const SortHelper &sort_helper);
     static int UpdateHashedDBRecord(const QString &hash, const QString &file_name,
                                     const QString &host);
     static QString VideoFileHash(const QString &file_name, const QString &host);
diff --git a/mythtv/programs/mythfrontend/globalsettings.cpp b/mythtv/programs/mythfrontend/globalsettings.cpp
index b90d080..eb611e0 100644
--- a/mythtv/programs/mythfrontend/globalsettings.cpp
+++ b/mythtv/programs/mythfrontend/globalsettings.cpp
@@ -2755,6 +2755,41 @@ ChannelGroupSettings::ChannelGroupSettings() :
     addTarget("1", new VerticalConfigurationGroup(true,false));
 };
 
+static HostCheckBox *SortIgnoreCase()
+{
+    HostCheckBox *gc = new HostCheckBox("SortIgnoreCase");
+    gc->setLabel(GeneralSettings::tr("Ignore case when sorting"));
+    gc->setValue(true);
+    gc->setHelpText(GeneralSettings::tr("If enabled, all sorting will be case-insensitive."));
+    return gc;
+}
+
+static HostCheckBox *SortIgnorePrefixes()
+{
+    HostCheckBox *gc = new HostCheckBox("SortIgnorePrefixes");
+
+    gc->setLabel(GeneralSettings::tr("Ignore prefixes when sorting"));
+    gc->setValue(true);
+    gc->setHelpText(GeneralSettings::tr("If enabled, video listings will "
+                                        "ignore common prefixes (The, A, An) when "
+                                        "sorting show names."));
+    return gc;
+}
+
+static HostLineEdit *SortIgnorePrefixExceptions()
+{
+    HostLineEdit *gc = new HostLineEdit("SortIgnorePrefixExceptions");
+
+    gc->setLabel(MainGeneralSettings::tr("Names exempt from prefix removal"));
+    gc->setValue("");
+    gc->setHelpText(MainGeneralSettings::tr("When stripping common prefixes (The, A, An) "
+					    "from filenames, this list of names "
+					    "will be exempt from that process. "
+					    "Enter multiple names separated by ';'."));
+    return gc;
+}
+
+
 // General RecPriorities settings
 
 static GlobalComboBox *GRSchedOpenEnd()
@@ -3862,6 +3897,9 @@ MainGeneralSettings::MainGeneralSettings()
     general->setLabel(tr("General"));
     general->addChild(UseVirtualKeyboard());
     general->addChild(ScreenShotPath());
+    general->addChild(SortIgnoreCase());
+    general->addChild(SortIgnorePrefixes());
+    general->addChild(SortIgnorePrefixExceptions());
     addChild(general);
 
     VerticalConfigurationGroup *media =
diff --git a/mythtv/programs/mythfrontend/playbackbox.cpp b/mythtv/programs/mythfrontend/playbackbox.cpp
index 0141a39..fbc4dd8 100644
--- a/mythtv/programs/mythfrontend/playbackbox.cpp
+++ b/mythtv/programs/mythfrontend/playbackbox.cpp
@@ -219,14 +219,13 @@ static PlaybackBox::ViewMask m_viewMaskToggle(PlaybackBox::ViewMask mask,
 static QString construct_sort_title(
     QString title, PlaybackBox::ViewMask viewmask,
     PlaybackBox::ViewTitleSort titleSort, int recpriority,
-    const QRegExp &prefixes)
+    const SortHelper &sortHelper)
 {
     if (title.isEmpty())
         return title;
 
-    QString sTitle = title;
+    QString sTitle = sortHelper.doTitle(title);
 
-    sTitle.remove(prefixes);
     if (viewmask == PlaybackBox::VIEW_TITLES &&
             titleSort == PlaybackBox::TitleSortRecPriority)
     {
@@ -386,7 +385,7 @@ void * PlaybackBox::RunPlaybackBox(void * player, bool showTV)
 PlaybackBox::PlaybackBox(MythScreenStack *parent, QString name,
                             TV *player, bool showTV)
     : ScheduleCommon(parent, name),
-      m_prefixes(QObject::tr("^(The |A |An )")),
+      m_sortHelper(),
       m_titleChaff(" \\(.*\\)$"),
       // UI variables
       m_recgroupList(NULL),
@@ -1721,7 +1720,7 @@ bool PlaybackBox::UpdateUILists(void)
                 {
                     sTitle = construct_sort_title(
                         p->GetTitle(), m_viewMask, titleSort,
-                        p->GetRecordingPriority(), m_prefixes);
+                        p->GetRecordingPriority(), m_sortHelper);
                     sTitle = sTitle.toLower();
 
                     if (!sortedList.contains(sTitle))
diff --git a/mythtv/programs/mythfrontend/playbackbox.h b/mythtv/programs/mythfrontend/playbackbox.h
index 6b7e144..236bd0a 100644
--- a/mythtv/programs/mythfrontend/playbackbox.h
+++ b/mythtv/programs/mythfrontend/playbackbox.h
@@ -24,6 +24,7 @@ using namespace std;
 
 #include "mythscreentype.h"
 #include "metadatafactory.h"
+#include "mythsorthelper.h"
 
 // mythfrontend
 #include "schedulecommon.h"
@@ -338,7 +339,7 @@ class PlaybackBox : public ScheduleCommon
     QString extract_commflag_state(const ProgramInfo &pginfo);
 
 
-    QRegExp m_prefixes;   ///< prefixes to be ignored when sorting
+    SortHelper m_sortHelper; ///< prefixes to be ignored when sorting
     QRegExp m_titleChaff; ///< stuff to remove for search rules
 
     MythUIButtonList *m_recgroupList;
diff --git a/mythtv/programs/mythfrontend/proglist.cpp b/mythtv/programs/mythfrontend/proglist.cpp
index 37e4506..72ef41e 100644
--- a/mythtv/programs/mythfrontend/proglist.cpp
+++ b/mythtv/programs/mythfrontend/proglist.cpp
@@ -27,6 +27,7 @@ using namespace std;
 #include "tv_actions.h"                 // for ACTION_CHANNELSEARCH
 #include "mythdb.h"
 #include "mythdate.h"
+#include "mythsorthelper.h"
 
 #define LOC      QString("ProgLister: ")
 #define LOC_WARN QString("ProgLister, Warning: ")
@@ -71,6 +72,8 @@ ProgLister::ProgLister(MythScreenStack *parent, ProgListType pltype,
     m_progList(NULL),
     m_messageText(NULL),
 
+    m_sortHelper(),
+
     m_allowViewDialog(true)
 {
     if (pltype == plMovies)
@@ -139,6 +142,8 @@ ProgLister::ProgLister(
     m_progList(NULL),
     m_messageText(NULL),
 
+    m_sortHelper(),
+
     m_allowViewDialog(true)
 {
 }
@@ -1384,16 +1389,13 @@ void ProgLister::FillItemList(bool restorePosition, bool updateDisp)
         LoadFromProgram(m_itemList, where, bindings, m_schedList);
     }
 
-    const QRegExp prefixes(
-        tr("^(The |A |An )",
-           "Regular Expression for what to ignore when sorting"));
     for (uint i = 0; i < m_itemList.size(); i++)
     {
         ProgramInfo *s = m_itemList[i];
         if (s)
         {
             s->sortTitle = (m_type == plTitle) ? s->GetSubtitle() : s->GetTitle();
-            s->sortTitle.remove(prefixes);
+            s->sortTitle = m_sortHelper.doTitle(s->sortTitle);
         }
     }
 
diff --git a/mythtv/programs/mythfrontend/proglist.h b/mythtv/programs/mythfrontend/proglist.h
index 39bb0de..e0c105d 100644
--- a/mythtv/programs/mythfrontend/proglist.h
+++ b/mythtv/programs/mythfrontend/proglist.h
@@ -9,6 +9,7 @@
 #include "programinfo.h" // for ProgramList
 #include "schedulecommon.h"
 #include "proglist_helpers.h"
+#include "mythsorthelper.h"
 
 enum ProgListType {
     plUnknown = 0,
@@ -128,6 +129,8 @@ class ProgLister : public ScheduleCommon
     MythUIButtonList *m_progList;
     MythUIText       *m_messageText;
 
+    SortHelper        m_sortHelper;
+
     bool              m_allowViewDialog;
 };
 
diff --git a/mythtv/programs/mythfrontend/programrecpriority.cpp b/mythtv/programs/mythfrontend/programrecpriority.cpp
index 4635873..924a5b5 100644
--- a/mythtv/programs/mythfrontend/programrecpriority.cpp
+++ b/mythtv/programs/mythfrontend/programrecpriority.cpp
@@ -406,7 +406,7 @@ ProgramRecPriority::ProgramRecPriority(MythScreenStack *parent,
                      m_lastRecordedText(NULL), m_lastRecordedDateText(NULL),
                      m_lastRecordedTimeText(NULL), m_channameText(NULL),
                      m_channumText(NULL), m_callsignText(NULL),
-                     m_recProfileText(NULL), m_currentItem(NULL)
+                     m_recProfileText(NULL), m_currentItem(NULL), m_sortHelper()
 {
     m_sortType = (SortType)gCoreContext->GetNumSetting("ProgramRecPrioritySorting",
                                                  (int)byTitle);
@@ -1208,8 +1208,7 @@ void ProgramRecPriority::FillList(void)
             {
                 ProgramRecPriorityInfo *progInfo = &(*it);
 
-                progInfo->sortTitle = progInfo->title;
-                progInfo->sortTitle.remove(QRegExp(tr("^(The |A |An )")));
+                progInfo->sortTitle = m_sortHelper.doTitle(progInfo->title);
 
                 progInfo->recType = recType;
                 progInfo->matchCount =
diff --git a/mythtv/programs/mythfrontend/programrecpriority.h b/mythtv/programs/mythfrontend/programrecpriority.h
index a876eb5..ea72135 100644
--- a/mythtv/programs/mythfrontend/programrecpriority.h
+++ b/mythtv/programs/mythfrontend/programrecpriority.h
@@ -5,6 +5,7 @@
 
 #include "recordinginfo.h"
 #include "mythscreentype.h"
+#include "mythsorthelper.h"
 
 // mythfrontend
 #include "schedulecommon.h"
@@ -129,6 +130,7 @@ class ProgramRecPriority : public ScheduleCommon
     bool m_reverseSort;
 
     SortType m_sortType;
+    SortHelper m_sortHelper;
 };
 
 Q_DECLARE_METATYPE(ProgramRecPriorityInfo *)
diff --git a/mythtv/programs/mythfrontend/videofilter.cpp b/mythtv/programs/mythfrontend/videofilter.cpp
index 2e82927..fc13bb5 100644
--- a/mythtv/programs/mythfrontend/videofilter.cpp
+++ b/mythtv/programs/mythfrontend/videofilter.cpp
@@ -79,7 +79,7 @@ VideoFilterSettings::VideoFilterSettings(bool loaddefaultsettings,
     m_parental_level(ParentalLevel::plNone), textfilter(""),
     season(-1), episode(-1), insertdate(QDate()),
     re_season("(\\d+)[xX](\\d*)"), re_date("-(\\d+)([dmw])"),
-    m_changed_state(0)
+    m_changed_state(0), m_sortHelper()
 {
     if (_prefix.isEmpty())
         prefix = "VideoDefault";
@@ -389,8 +389,7 @@ bool VideoFilterSettings::matches_filter(const VideoMetadata &mdata) const
 
 /// Compares two VideoMetadata instances
 bool VideoFilterSettings::meta_less_than(const VideoMetadata &lhs,
-                                         const VideoMetadata &rhs,
-                                         bool sort_ignores_case) const
+                                         const VideoMetadata &rhs) const
 {
     bool ret = false;
     switch (orderby)
@@ -407,9 +406,9 @@ bool VideoFilterSettings::meta_less_than(const VideoMetadata &lhs,
             else
             {
                 lhs_key = VideoMetadata::GenerateDefaultSortKey(lhs,
-                                                           sort_ignores_case);
+								m_sortHelper);
                 rhs_key = VideoMetadata::GenerateDefaultSortKey(rhs,
-                                                           sort_ignores_case);
+								m_sortHelper);
             }
             ret = lhs_key < rhs_key;
             break;
@@ -433,9 +432,9 @@ bool VideoFilterSettings::meta_less_than(const VideoMetadata &lhs,
                 else
                 {
                     lhs_key = VideoMetadata::GenerateDefaultSortKey(lhs,
-                                                               sort_ignores_case);
+								    m_sortHelper);
                     rhs_key = VideoMetadata::GenerateDefaultSortKey(rhs,
-                                                               sort_ignores_case);
+								    m_sortHelper);
                 }
                 ret = lhs_key < rhs_key;
             }
@@ -463,10 +462,8 @@ bool VideoFilterSettings::meta_less_than(const VideoMetadata &lhs,
         }
         case kOrderByFilename:
         {
-            QString lhsfn(sort_ignores_case ?
-                          lhs.GetFilename().toLower() : lhs.GetFilename());
-            QString rhsfn(sort_ignores_case ?
-                          rhs.GetFilename().toLower() : rhs.GetFilename());
+            QString lhsfn = m_sortHelper.doFilename(lhs.GetFilename());
+            QString rhsfn = m_sortHelper.doFilename(rhs.GetFilename());
             ret = naturalCompare(lhsfn, rhsfn) < 0;
             break;
         }
diff --git a/mythtv/programs/mythfrontend/videofilter.h b/mythtv/programs/mythfrontend/videofilter.h
index d518abf..6bee2e1 100644
--- a/mythtv/programs/mythfrontend/videofilter.h
+++ b/mythtv/programs/mythfrontend/videofilter.h
@@ -4,6 +4,7 @@
 // MythTV headers
 #include "mythscreentype.h"
 #include "parentalcontrols.h"
+#include "mythsorthelper.h"
 
 // Qt headers
 #include <QCoreApplication>
@@ -48,8 +49,7 @@ class VideoFilterSettings
     VideoFilterSettings &operator=(const VideoFilterSettings &rhs);
 
     bool matches_filter(const VideoMetadata &mdata) const;
-    bool meta_less_than(const VideoMetadata &lhs, const VideoMetadata &rhs,
-                        bool sort_ignores_case) const;
+    bool meta_less_than(const VideoMetadata &lhs, const VideoMetadata &rhs) const;
 
     void saveAsDefault();
 
@@ -190,8 +190,9 @@ class VideoFilterSettings
     const QRegExp re_season;
     const QRegExp re_date;
 
-
     unsigned int m_changed_state;
+
+    SortHelper m_sortHelper;
 };
 
 struct FilterSettingsProxy
diff --git a/mythtv/programs/mythfrontend/videolist.cpp b/mythtv/programs/mythfrontend/videolist.cpp
index 9c32b2d..032cb8a 100644
--- a/mythtv/programs/mythfrontend/videolist.cpp
+++ b/mythtv/programs/mythfrontend/videolist.cpp
@@ -149,28 +149,25 @@ QString TreeNodeData::GetPrefix(void) const
 /// metadata sort function
 struct metadata_sort
 {
-    metadata_sort(const VideoFilterSettings &vfs, bool sort_ignores_case) :
-        m_vfs(vfs), m_sic(sort_ignores_case) {}
+    metadata_sort(const VideoFilterSettings &vfs) : m_vfs(vfs) {}
 
     bool operator()(const VideoMetadata *lhs, const VideoMetadata *rhs)
     {
-        return m_vfs.meta_less_than(*lhs, *rhs, m_sic);
+        return m_vfs.meta_less_than(*lhs, *rhs);
     }
 
     bool operator()(const smart_meta_node &lhs, const smart_meta_node &rhs)
     {
-        return m_vfs.meta_less_than(*(lhs->getData()), *(rhs->getData()),
-                                    m_sic);
+        return m_vfs.meta_less_than(*(lhs->getData()), *(rhs->getData()));
     }
 
   private:
     const VideoFilterSettings &m_vfs;
-    bool m_sic;
 };
 
 struct metadata_path_sort
 {
-    explicit metadata_path_sort(bool ignore_case) : m_ignore_case(ignore_case) {}
+    explicit metadata_path_sort(void) : m_sortHelper() {}
 
     bool operator()(const VideoMetadata &lhs, const VideoMetadata &rhs)
     {
@@ -187,15 +184,6 @@ struct metadata_path_sort
         return sort(lhs->getPath(), rhs->getPath());
     }
 
-  private:
-    const QRegExp &getTrim(void)
-    {
-        static QString pattern(VideoMetadata::tr("^(The |A |An )"));
-	if (m_ignore_case)
-         return QRegExp(prefixes, Qt::CaseInsensitive);
-       return QRegExp(prefixes, Qt::CaseSensitive);
-    }
-
    bool sort(const VideoMetadata *lhs, const VideoMetadata *rhs)
     {
         return sort(lhs->GetFilename(), rhs->GetFilename());
@@ -203,18 +191,12 @@ struct metadata_path_sort
 
     bool sort(const QString &lhs, const QString &rhs)
     {
-        const QRegExp prefixes = getTrim();
-        QString lhs_comp = QString(lhs).remove(prefixes);
-        QString rhs_comp = QString(rhs).remove(prefixes);
-        if (m_ignore_case)
-        {
-            lhs_comp = lhs_comp.toLower();
-            rhs_comp = rhs_comp.toLower();
-        }
+        QString lhs_comp = m_sortHelper.doFilename(lhs);
+        QString rhs_comp = m_sortHelper.doFilename(rhs);
         return naturalCompare(lhs_comp, rhs_comp) < 0;
     }
 
-    bool m_ignore_case;
+    SortHelper m_sortHelper;
 };
 
 static QString path_to_node_name(const QString &path)
@@ -476,6 +458,8 @@ class VideoListImp
     metadata_list_type m_metadata_list_type;
 
     VideoFilterSettings m_video_filter;
+
+    SortHelper m_sortHelper;
 };
 
 VideoList::VideoList()
@@ -558,7 +542,8 @@ void VideoList::InvalidateCache(void)
 // VideoListImp
 //////////////////////////////
 VideoListImp::VideoListImp() : m_metadata_view_tree("", "top"),
-                               m_metadata_list_type(ltNone)
+                               m_metadata_list_type(ltNone),
+			       m_sortHelper()
 {
     m_ListUnknown = gCoreContext->GetNumSetting("VideoListUnknownFileTypes", 0);
 
@@ -760,13 +745,12 @@ void VideoListImp::sort_view_data(bool flat_list)
     if (flat_list)
     {
         sort(m_metadata_view_flat.begin(), m_metadata_view_flat.end(),
-             metadata_sort(m_video_filter, true));
+             metadata_sort(m_video_filter));
     }
     else
     {
-        m_metadata_view_tree.sort(metadata_path_sort(true),
-                                  metadata_sort(m_video_filter,
-                                                true));
+        m_metadata_view_tree.sort(metadata_path_sort(),
+                                  metadata_sort(m_video_filter));
     }
 }
 
@@ -820,7 +804,7 @@ void VideoListImp::buildGroupList(metadata_list_type whence)
     transform(m_metadata.getList().begin(), m_metadata.getList().end(),
               mli, to_metadata_ptr());
 
-    metadata_path_sort mps(true);
+    metadata_path_sort mps = metadata_path_sort();
     sort(mlist.begin(), mlist.end(), mps);
 
     typedef map<QString, meta_dir_node *> group_to_node_map;
@@ -953,7 +937,7 @@ void VideoListImp::buildTVList(void)
     transform(m_metadata.getList().begin(), m_metadata.getList().end(),
               mli, to_metadata_ptr());
 
-    metadata_path_sort mps(true);
+    metadata_path_sort mps = metadata_path_sort();
     sort(mlist.begin(), mlist.end(), mps);
 
     meta_dir_node *video_root = &m_metadata_tree;
@@ -999,7 +983,7 @@ void VideoListImp::buildDbList()
 
 //    print_meta_list(mlist);
 
-    metadata_path_sort mps(true);
+    metadata_path_sort mps = metadata_path_sort();
     sort(mlist.begin(), mlist.end(), mps);
 
     // TODO: break out the prefix in the DB so this isn't needed
@@ -1163,7 +1147,7 @@ void VideoListImp::update_meta_view(bool flat_list)
         if (!(*si)->HasSortKey())
         {
             VideoMetadata::SortKey skey =
-                VideoMetadata::GenerateDefaultSortKey(*(*si), true);
+                VideoMetadata::GenerateDefaultSortKey(*(*si), m_sortHelper);
             (*si)->SetSortKey(skey);
         }
     }
