Files
PicardScripts/SCRIPT_GUIDE.md
2026-01-31 12:23:10 +01:00

72 KiB

Picard File Naming Script - Technical Guide

Complete technical reference for MusicBrainz Picard File Naming Script v3.0

Note: This guide references Picard_Rename_Script.txt as the working script file. For importing into Picard, use Picard_Rename_Script.ptsp (Picard Script Package format).


Table of Contents

  1. How Picard Scripting Works
  2. Script Execution Flow
  3. Complete Configuration Options
  4. Character Replacement
  5. VBR Bitrate Mapping
  6. Path Generation Examples
  7. Advanced Features
  8. Variables Reference
  9. Customization Guide

1. How Picard Scripting Works

1.1 What is TaggerScript?

TaggerScript is Picard's built-in scripting language for file naming and tag manipulation. It allows you to:

  • Build file and folder paths dynamically from metadata
  • Perform conditional logic based on tag values
  • Transform and clean up metadata
  • Set custom variables for use later in the script

1.2 Basic Syntax

Functions are called with $function(arguments)

$upper(hello)           -> HELLO
$left(Beatles,4)        -> Beat
$if(condition,then,else) -> Conditional logic

Variables are referenced with %variable%

%artist%       -> Tag value (e.g., "The Beatles")
%_variable%    -> Internal variable (starts with underscore)

Setting Variables uses $set(name,value)

$set(_myvar,Hello)      -> Creates variable %_myvar% = "Hello"

Comments use $noop(text)

$noop( This is a comment )   -> Does nothing, for documentation

1.3 Key Concepts

Tags vs Variables:

  • Tags come from MusicBrainz or existing file metadata: %artist%, %album%, %tracknumber%
  • Variables are created by the script: %_myvar%, %_isLive%, %_nFilePath%

Execution Order:

  • Scripts execute top-to-bottom
  • Variables must be defined before they're used
  • The final output is whatever the script "returns" (last non-$noop statement)

String Concatenation:

  • Just put values next to each other: %artist% - %title% -> "Beatles - Yesterday"
  • Use / for path separators: %artist%/%album%/ -> "Beatles/Abbey Road/"

2. Script Execution Flow

2.1 Visual Flow Diagram

┌─────────────────────────────────────────────────────────────┐
│ START: File needs to be renamed                             │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 1: Load Constants                                   │
│ - MusicBrainz IDs                                           │
│ - Default display names                                     │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 2: Read User Configuration                          │
│ - All 60+ settings loaded                                   │
│ - Determines how path will be built                         │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 3: Setup Default Variables                          │
│ - Fallbacks if plugin not loaded                            │
│ - Fallbacks if metadata missing                             │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 4: Initialize Working Variables                     │
│ - Disc/track numbers                                        │
│ - Calculate padding lengths                                 │
│ - Featured artist detection                                 │
│ - Extract year                                              │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 5: Enhance Album Title                              │
│ - Add disambiguation, year, label, catalog                  │
│ - Trim if too long                                          │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 6: Detect Music Types                               │
│ - Set flags: _isAlbum, _isSingle, _isLive, etc.            │
│ - Detects: Album, Single, EP, Live, Soundtrack, etc.        │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 7: Clean Up Tags                                    │
│ - Remove placeholder tags with default values               │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 8: Setup Filename Variables                         │
│ - Create sanitized versions for file/folder names           │
│ - Remove "The " prefix for sorting                          │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 9: Apply Character Filtering                        │
│ - Tag-level replacements (written to file)                  │
│ - Filename-level replacements (paths only)                  │
│ - Ensure cross-platform compatibility                       │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 10: Detect Audio Metrics                            │
│ - Determine CBR vs VBR                                      │
│ - Map VBR bitrate to quality level (V0-V9)                  │
│ - Extract sample rate, bit depth, channels                  │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 11: Build Directory Path                            │
│ - Apply genre subsort (if enabled)                          │
│ - Route special cases (Soundtrack, Various, etc.)           │
│ - Build artist letter folder                                │
│ - Build artist name folder                                  │
│ - Add type subfolder (Albums/, Singles/, etc.)              │
│ - Build album folder with metadata                          │
│ - Add disc subfolder (if multi-disc)                        │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ SECTION 12: Build Filename                                  │
│ - Track number (or vinyl style A1, B1)                      │
│ - Track title                                               │
│ - Duration                                                  │
│ - Audio quality metrics                                     │
└────────────────────┬────────────────────────────────────────┘
                     │
┌────────────────────▼────────────────────────────────────────┐
│ OUTPUT: Complete path                                       │
│ /B/Beatles, The/(1969) Abbey Road [CD - MP3]/01. Come Together... │
└─────────────────────────────────────────────────────────────┘

2.2 Step-by-Step Execution

Step 1: Constants Loading

  • MusicBrainz special IDs loaded
  • Default names set ([Unknown Artist], [Various Artists], etc.)
  • Regex constants defined

Step 2: Configuration Loading

  • All user settings loaded
  • Settings determine which sections execute
  • Settings control what metadata is shown

Step 3: Default Variables

  • Plugin variables loaded with fallbacks
  • If "Additional Artists Variables" plugin not present, uses basic tags
  • Album and track titles get default values if missing

Step 4: Working Variables Initialization

  • Disc and track numbers extracted
  • Padding calculated based on total counts
  • Featured artists detected by comparing album vs track artist
  • Year extracted from date tags

Step 5: Album Title Enhancement

  • Disambiguation comment added if present
  • Release year, label, catalog added if enabled
  • Title trimmed if longer than max length

Step 6: Music Type Detection

  • All release type flags set based on MusicBrainz tags
  • Special cases detected (Various Artists, Tribute, Cover, etc.)
  • Incomplete status determined

Step 7: Tag Cleanup

  • Placeholder tags removed if they still contain defaults
  • Prevents "Title", "Artist" from being written to files

Step 8: Filename Variables Setup

  • Sanitized versions created for all metadata used in paths
  • Sort tags used as fallbacks
  • "The " prefix removed for sorting

Step 9: Character Filtering

  • Tag-level replacements (written to actual file metadata)
  • Filename-level replacements (used in paths only)
  • Ensures Windows/Linux/macOS/Samba compatibility

Step 10: Audio Metrics Detection

  • Bitrate analyzed to determine CBR vs VBR
  • VBR mapped to quality level (V0-V9)
  • Sample rate, bit depth, channels extracted

Step 11: Path Generation

  • Genre subsort applied first (if enabled)
  • Special collections routed (Soundtrack, Various, Audiobooks)
  • Artist letter folder created
  • Artist name folder created
  • Type subfolder added (if enabled)
  • Album folder built with all metadata
  • Disc subfolder added (if multi-disc)

Step 12: Filename Generation

  • Track number formatted (padded or vinyl style)
  • Track title added
  • Duration added (if enabled)
  • Audio quality added (if enabled)

Output:

  • Complete path returned to Picard
  • Picard moves/renames file to this location

3. Complete Configuration Options

3.1 All Settings Reference Table

Variable Type Default Values Description
DEVELOPMENT SETTINGS
_devMode Integer 0 0, 1 Use test values (1) or real metadata (0)
_quickNoNameFormat Integer 0 0, 1 Skip formatting (1) or full format (0)
DISPLAY OPTIONS
_showDate Integer 1 0, 1 Show year in album folder name
_showRecordLabel Integer 0 0, 1 Show record label in album folder
_showReleaseStatus Integer 0 0, 1 Show release status (Official, Promotion, etc.)
_showCatalogueNumber Integer 0 0, 1 Show catalog number in album folder
_showIDNum Integer 1 0, 1 Show MusicBrainz ID and catalog
_showTime Integer 1 0, 1 Show track duration in filename
_showBandwidth Integer 1 0, 1 Show audio quality metrics in filename
PRIMARY ORGANIZATION
_orderTypeForRoot Integer 2 1, 2 1=Category, 2=Artist letter folders
_orderTypeForArtist Integer 1 1, 2, 3 1=First name, 2=Last name, 3=None
_separateByTypeInArtistDirectory Integer 1 0, 1 Separate albums/singles/EPs into subfolders
_separateAlbum Integer 0 0, 1 Put albums in Albums/ subfolder
_rootLevelTypeSeparation Integer 0 0, 1 Separate by file type at root (/MP3/, /FLAC/)
_albumLevelTypeSeparation Integer 0 0, 1 Separate by file type in album
_albumNameAtTypeSeparation Integer 0 0, 1 Show album name before type folder
INCOMPLETE ALBUMS
_extraTrackHandling Integer 1 0, 1 How to handle albums with extra tracks
_earlierPresortForIncompletes Integer 1 0, 1 Separate incomplete albums early
MULTI-DISC
_useSubDiscDirectory Integer 1 0, 1 Multi-disc albums in disc subfolders
_mergeDiscWhenNotUsingSubDirectory Integer 0 0, 1 Skip disc folder if only one disc
_showDiscSubtitle Integer 1 0, 1 Show disc subtitle if present
_nameForTypeCD String Disc - Name for CD disc folders
_nameForTypeVinyl String Side - Name for vinyl disc folders
_useMusicBrainzStyleForVinylTrack Integer 1 0, 1 Use A1, B1 style for vinyl tracks
SPECIAL COLLECTIONS
_soundTracksDirectory String Soundtrack/ - Soundtrack albums folder name
_variousArtistsDirectory String Various/ - Various Artists folder name
_compilationsGSubDirectory String Compilations/ - Global compilations folder name
_audiobooksDirectory String Audiobook/ - Audiobooks folder name
_podcastSubDirectory String Podcast/ - Podcasts folder name
_incompleteDirectory String Partial - Incomplete albums suffix/folder name
TYPE SUBFOLDER NAMES
_albumSubDirectory String Albums/ - Albums subfolder name
_compilationsASubDirectory String Compilation/ - Artist compilations subfolder
_coverSubDirectory String Cover/ - Cover albums subfolder
_tributeSubDirectory String Tribute/ - Tribute albums subfolder
_singlesSubDirectory String Singles/ - Singles subfolder
_liveSubDirectory String Live/ - Live albums subfolder
_epSubDirectory String EP/ - EPs subfolder
_broadcastSubDirectory String Broadcast/ - Broadcasts subfolder
_interviewSubDirectory String Interview/ - Interviews subfolder
_videoSubDirectory String Video/ - Videos subfolder
_otherSubDirectory String Others/ - Other releases subfolder
GENRE SUBSORT
_isSubSort Integer 1 0, 1 Enable genre-based pre-sorting
_subSortGame String Arcade/ - Game soundtracks folder
_subSortDJBits String DJBits/ - DJ/remix folder
_subSortClassical String Classical/ - Classical music folder
_subSortDemento String Dementia/ - Comedy/novelty folder
_subSort12Inch String 12 Inch Mix/ - 12" mixes folder
_subSortDisney String Disney/ - Disney music folder
_subSortPodcast String Podcast/ - Podcasts folder
_subSortInterview String Interview/ - Interviews folder
_subSortBroadcast String Broadcast/ - Broadcasts folder
_subSortReserved String Singles Candidates/ - Reserved/special folder
_subSortPreTag String No MBID/ - Untagged folder
_subSortHoliday String Holiday/ - Holiday music folder
_subSortCountry String Country/ - Country music folder
_subSortBlues String Blues/ - Blues music folder
_subSortJazz String Jazz/ - Jazz music folder
_subSort2Oct String Spooktacular/ - October seasonal folder
_subSort2Nov String Fallback/ - November seasonal folder
_subSort2Dec String Here Comes Santa/ - December seasonal folder
_subSort2Jan String Wintertime/ - January seasonal folder
_subSort2Feb String Will You Be My Valentine?/ - February seasonal folder
_subSort2Mar String Spring is in the Air/ - March seasonal folder
_subSort2Apr String Foolish/ - April seasonal folder
_subSort2May String Maybe/ - May seasonal folder
_subSort2June String SumSumSummertime/ - June seasonal folder
_subSort2July String Fireworks & Stuff/ - July seasonal folder
_subSort2Aug String SumSumSummertime/ - August seasonal folder
_subSort2Sept String SumSumSummertime/ - September seasonal folder
TRIBUTE/COVER
_altArtistSort Integer 1 0, 1 File tribute/cover under original artist
TRACK SEPARATION
_showTrackArtistSeparation Integer 0 0, 1 Separate tracks by artist in album
LENGTH/PADDING
_PaddedDiscNumMinLength Integer 1 1-9 Minimum disc number padding
_PaddedTrackNumMinLength Integer 2 1-9 Minimum track number padding
_aTitleMaxLength Integer 65 1-999 Maximum album title length
_tTitleMaxLength Integer 65 1-999 Maximum track title length
_tFilenameMaxLength Integer 120 1-999 Maximum complete filename length

3.2 Development Settings

_devMode

Purpose: Test the script with hardcoded values instead of real metadata.

Values:

  • 0 - Normal operation (use real file metadata)
  • 1 - Test mode (use hardcoded values defined in Section 10)

When to use:

  • Testing script changes without actual music files
  • Debugging audio metrics detection
  • Verifying path generation logic

WARNING: Must be set to 0 for actual use! If left at 1, all files will use the same test values.

Test values (when _devMode = 1):

$set(_biitrate,71.426)           # Test bitrate
$set(_saample_rate,44100)        # Test sample rate
$set(_biits_per_sample,16)       # Test bit depth
$set(_chaannels,2)               # Test channels
$set(_tiitle,My Great Score)     # Test title

_quickNoNameFormat

Purpose: Skip filename formatting for quick sorting from unmatched files.

Values:

  • 0 - Full formatting with all metadata (default)
  • 1 - Minimal formatting (keeps original filename)

When to use:

  • Sorting large batches of unmatched files quickly
  • When you just want directory organization, not filename changes

Effect:

  • Disables _showTime and _showBandwidth automatically
  • Uses %_filename% instead of %_titleForFilename%
  • Still organizes into folders normally

3.3 Display Options

_showDate

Purpose: Show release year in album folder name.

Values:

  • 0 - Album name only
  • 1 - Album name with year (default)

Examples:

_showDate = 0:  /Artist/Abbey Road [CD - MP3]/
_showDate = 1:  /Artist/(1969) Abbey Road [CD - MP3]/

Notes:

  • Uses first available: originalyear, originaldate, date
  • Shows first 4 characters (year only, not full date)
  • Shows "0000" if no date available

_showRecordLabel

Purpose: Show record label in album folder name.

Values:

  • 0 - Don't show label (default)
  • 1 - Show label

Examples:

_showRecordLabel = 0:  /Artist/(1985) Album [CD - MP3]/
_showRecordLabel = 1:  /Artist/(1985) Album [Epic Records] [CD - MP3]/

Notes:

  • Only shows first label if multiple
  • Requires label tag to be present

_showReleaseStatus

Purpose: Show release status (Official, Promotion, Bootleg, etc.) in album folder.

Values:

  • 0 - Don't show status (default)
  • 1 - Show status

Examples:

_showReleaseStatus = 0:  /Artist/(1985) Album [CD - MP3]/
_showReleaseStatus = 1:  /Artist/(1985) Album [Promotion] [CD - MP3]/

Common statuses:

  • Official
  • Promotion
  • Bootleg
  • Pseudo-Release

_showCatalogueNumber

Purpose: Show catalog number in album folder name.

Values:

  • 0 - Don't show catalog number (default)
  • 1 - Show catalog number

Examples:

_showCatalogueNumber = 0:  /Artist/(1985) Album [CD - MP3]/
_showCatalogueNumber = 1:  /Artist/(1985) Album [XPCD-1234] [CD - MP3]/

_showIDNum

Purpose: Show MusicBrainz Album ID and catalog number.

Values:

  • 0 - Don't show
  • 1 - Show (default)

Format: [mbid] {catalog}

Examples:

_showIDNum = 0:  /Artist/(1985) Album [CD - MP3]/
_showIDNum = 1:  /Artist/(1985) Album [CD - MP3] [a1b2c3d4] {XPCD-1234}/

Use case: Helps identify exact MusicBrainz release if you have multiple versions

_showTime

Purpose: Show track duration in filename.

Values:

  • 0 - Don't show duration
  • 1 - Show duration (default)

Format: [XmYYs]

Examples:

_showTime = 0:  01. Come Together.mp3
_showTime = 1:  01. Come Together [4m20s].mp3

Notes:

  • Automatically disabled if _quickNoNameFormat = 1
  • Uses Picard's %_length% variable
  • Format: minutes + "m" + seconds + "s"

_showBandwidth

Purpose: Show audio quality metrics in filename.

Values:

  • 0 - Don't show metrics
  • 1 - Show metrics (default)

Format: [bitrate samplerate type channels]

Examples:

_showBandwidth = 0:  01. Track.mp3
_showBandwidth = 1:  01. Track [320 44100KHz CBR 2ch].mp3
_showBandwidth = 1:  02. Track [V0 44100KHz VBR 2ch].mp3
_showBandwidth = 1:  03. Track [96000KHz 24bit 6ch].flac

Metrics shown:

  • Bitrate: 320, V0, V2, etc. (see VBR Mapping section)
  • Sample Rate: 44100KHz, 48000KHz, 96000KHz, etc. (full Hz value)
  • Type: CBR, VBR, or file format for lossless
  • Channels: 2ch (stereo), 6ch (5.1 surround), etc.

3.4 Primary Organization Structure

_orderTypeForRoot

Purpose: Choose root directory organization method.

Values:

  • 1 - By category/genre (requires Last.fm.ng plugin)
  • 2 - By artist first letter (default, recommended)

Examples:

Option 1 - Category:

/Rock/
  Beatles, The/(1969) Abbey Road [CD - MP3]/...
  Pink Floyd/(1973) Dark Side of the Moon [Vinyl - FLAC]/...
/Pop/
  Madonna/(1984) Like a Virgin [CD - MP3]/...
  Taylor Swift/(2014) 1989 [CD - MP3]/...

Option 2 - Artist Letter:

/B/
  Beatles, The/(1969) Abbey Road [CD - MP3]/...
/M/
  Madonna/(1984) Like a Virgin [CD - MP3]/...
/P/
  Pink Floyd/(1973) Dark Side of the Moon [Vinyl - FLAC]/...

Notes:

  • Option 1 requires albumgrouping tag (from Last.fm.ng plugin)
  • Option 2 is most common and doesn't require extra plugins

_orderTypeForArtist

Purpose: Choose how artist names are sorted.

Values:

  • 1 - First letter of first name (default)
  • 2 - First letter of last name (uses sort tags)
  • 3 - No alphabetical separation

Examples:

Option 1 - First Name:

/M/Madonna/...
/W/Weird Al Yankovic/...
/T/The Beatles/...

Option 2 - Last Name:

/M/Madonna/...
/Y/Yankovic, Weird Al/...
/B/Beatles, The/...

Option 3 - No Separation:

/Madonna/...
/Weird Al Yankovic/...
/The Beatles/...

Notes:

  • Option 2 relies on MusicBrainz albumartistsort and artistsort tags
  • "The", "A", "An" are automatically handled by MusicBrainz sort tags
  • Option 3 can create very long lists in root directory

_separateByTypeInArtistDirectory

Purpose: Separate releases by type into subfolders.

Values:

  • 0 - All releases directly in artist folder
  • 1 - Separate into subfolders (default)

Examples:

Option 0 - No Separation:

/Artist/
  (1969) Abbey Road [CD - MP3]/...
  (1967) All You Need is Love [CD - MP3]/...  (single)
  (1994) Live at the BBC [CD - MP3]/...       (live)

Option 1 - With Separation:

/Artist/
  (1969) Abbey Road [CD - MP3]/...
  Singles/
    (1967) All You Need is Love [CD - MP3]/...
  Live/
    (1994) Live at the BBC [CD - MP3]/...

Subfolder types created:

  • Albums/ (if _separateAlbum = 1)
  • Singles/
  • EP/
  • Live/
  • Compilation/
  • Cover/
  • Tribute/
  • Broadcast/
  • Interview/
  • Video/
  • Others/

_separateAlbum

Purpose: Put regular albums in an Albums/ subfolder.

Values:

  • 0 - Albums directly in artist folder (default)
  • 1 - Albums in Albums/ subfolder

Requires: _separateByTypeInArtistDirectory = 1

Examples:

Option 0:

/Artist/
  (1969) Abbey Road [CD - MP3]/...
  (1965) Rubber Soul [CD - MP3]/...
  Singles/
    (1967) All You Need is Love [CD - MP3]/...

Option 1:

/Artist/
  Albums/
    (1969) Abbey Road [CD - MP3]/...
    (1965) Rubber Soul [CD - MP3]/...
  Singles/
    (1967) All You Need is Love [CD - MP3]/...

When to use: Some users prefer all release types in subfolders for consistency.


3.5 Multi-Disc Handling

_useSubDiscDirectory

Purpose: Create separate subdirectories for each disc in multi-disc albums.

Values:

  • 0 - All discs in same folder with disc prefix in track number
  • 1 - Each disc in its own subfolder (default)

Examples:

Option 0 - Same Folder:

/Artist/Album (1985)/
  101. Track One.mp3
  102. Track Two.mp3
  201. Track One.mp3
  202. Track Two.mp3

Option 1 - Disc Subfolders:

/Artist/(1985) Album [CD - MP3]/
  Disc01/
    01. Track One.mp3
    02. Track Two.mp3
  Disc02/
    01. Track One.mp3
    02. Track Two.mp3

Notes:

  • Option 0 is useful for devices that don't support subfolders
  • Option 1 is cleaner and more organized

_showDiscSubtitle

Purpose: Show disc subtitle if present in MusicBrainz data.

Values:

  • 0 - Just disc number
  • 1 - Include subtitle (default)

Examples:

Option 0:

/Album/Disc01/...
/Album/Disc02/...

Option 1:

/Album/Disc01 - Acoustic/...
/Album/Disc02 - Electric/...

Notes:

  • Only applies when _useSubDiscDirectory = 1
  • Disc subtitles come from MusicBrainz, not always present

_useMusicBrainzStyleForVinylTrack

Purpose: Use vinyl-style track numbering (A1, A2, B1, B2) for vinyl releases.

Values:

  • 0 - Standard numbering (01, 02, 03)
  • 1 - Vinyl style (A1, B1) (default)

Applies to: Media type = "Vinyl" only

Examples:

Option 0 - Standard:

/Album [Vinyl - MP3]/
  Side 1/
    01. Track.mp3
    02. Track.mp3
  Side 2/
    01. Track.mp3
    02. Track.mp3

Option 1 - Vinyl Style:

/Album [Vinyl - MP3]/
  Side 1/
    A1. Track.mp3
    A2. Track.mp3
  Side 2/
    B1. Track.mp3
    B2. Track.mp3

Requirements:

  • Release must have MusicBrainz track numbers (not all do)
  • Media tag must be "Vinyl"

3.6 Genre SubSort

How Genre SubSort Works

Genre SubSort creates custom root-level folders based on the genresort tag. This is an advanced feature for organizing large, diverse libraries.

Workflow:

  1. Set custom genresort tag on files (not from MusicBrainz)
  2. Script detects keyword in genresort value
  3. Routes to corresponding subsort folder

Example:

  • Tag: genresort = Holiday
  • Trigger: Script detects "Holiday" in tag
  • Folder: _subSortHoliday = Holiday/
  • Result: /Holiday/Artist/Album/

Available Subsort Categories

Trigger Keyword Folder Variable Default Folder Use Case
Holiday _subSortHoliday Holiday/ Christmas, seasonal music
Classical _subSortClassical Classical/ Classical music
Jazz _subSortJazz Jazz/ Jazz music
Blues _subSortBlues Blues/ Blues music
Country _subSortCountry Country/ Country music
Game _subSortGame Arcade/ Video game soundtracks
Disney _subSortDisney Disney/ Disney music
odcast _subSortPodcast Podcast/ Podcasts
nterview _subSortInterview Interview/ Interviews
roadcast _subSortBroadcast Broadcast/ Broadcasts
12 Inch _subSort12Inch 12 Inch Mix/ 12" remix singles
Novelty, Comedy, Demento, FuMP _subSortDemento Dementia/ Comedy/novelty music
DJ Bits _subSortDJBits DJBits/ DJ tools, samples
*-* _subSortReserved Singles Candidates/ Special marker
*** _subSortPreTag No MBID/ Untagged files

Seasonal Subsort (Second Level)

You can also use seasonal keywords for a second level of sorting:

Trigger Keyword Folder Season
Spook Spooktacular/ Halloween/October
Fall Fallback/ November
Santa Here Comes Santa/ December
Winter Wintertime/ January
Valentine Will You Be My Valentine?/ February
Spring Spring is in the Air/ March
Fool Foolish/ April
Maybe Maybe/ May
Summer, Firew SumSumSummertime/, Fireworks & Stuff/ June-September

Example:

genresort = Holiday Santa
-> Routes to: /Holiday/Here Comes Santa/Artist/Album/

Creating Your Own Subsort

  1. Define folder name:
$set(_subSortMyGenre,MyGenre/)
  1. Add detection logic in Section 11:
$if($in(%genresort%,MyKeyword),$set(_subSortDirectory,%_subSortMyGenre%))
  1. Tag your files:
genresort = MyKeyword
  1. Result:
/MyGenre/Artist/Album/

4. Character Replacement

4.1 Why Character Replacement?

Different operating systems and filesystems have different rules for allowed characters in file and folder names:

  • Windows: Disallows :, ?, *, <, >, |, ", /, \
  • Linux/macOS: More permissive but / still reserved for path separator
  • Samba/CIFS: Network shares have additional restrictions

Additionally, some characters can cause issues with:

  • Command-line tools
  • Backup software
  • Cloud storage sync
  • Media players

This script ensures cross-platform compatibility by replacing problematic characters.

4.2 Complete Replacement Table

Tag-Level Replacements (Written to File Metadata)

These replacements modify the actual tags written to your music files:

Original Replacement Tags Affected Reason Example
... & album, title, discsubtitle Ellipsis standardization "Best... Song" -> "Best & Song"
No. X X album, title, discsubtitle Remove "No." prefix "No. 1 Hit" -> "1 Hit"
12" 12 Inch album, title, discsubtitle, media Standardize vinyl notation '12" Vinyl' -> "12 Inch Vinyl"
"text" 'text' All artist/album/title tags Samba compatibility 'The "Best"' -> "The 'Best'"

Why tag-level? These improve consistency and readability of your metadata, not just filenames.

Filename-Level Replacements (File/Folder Names Only)

These replacements only affect paths, not file metadata:

Original Replacement Scope Reason Example
# - All filename variables Hash alternative "Track #1" -> "Track -1"
: _ All filename variables Windows incompatible "Title: Sub" -> "Title_ Sub"
? G All filename variables Windows incompatible "Why?" -> "WhyG"
| è Album, title, disc subtitle Pipe alternative "A|B" -> "Aèb"
> [removed] Album, title, disc subtitle Windows incompatible "A>B" -> "AB"
< [removed] Album, title, disc subtitle Windows incompatible "A<B" -> "AB"
* 1 All variables Windows incompatible "A*B" -> "A1B"
& & All variables HTML entity "A & B" -> "A & B"

Why filename-only? These are purely for filesystem compatibility, no need to modify the actual metadata.

4.3 Scope: Which Variables Are Affected?

Tag-Level Scope (all of these):

  • album
  • title
  • discsubtitle
  • media
  • albumartist
  • artist
  • albumartistsort
  • artistsort

Filename-Level Scope (all of these):

  • _titleForFilename
  • _albumForFilename
  • _discsubtitleForFilename
  • _artistForFilename
  • _albumartistForFilename
  • _artistsortForFilename
  • _albumartistsortForFilename

4.4 Platform-Specific Issues

Windows Path Restrictions

Windows disallows these characters in paths: < > : " / \ | ? *

How the script handles it:

  • : -> _ (colon to underscore)
  • ? -> G (question mark removed)
  • * -> 1 (asterisk to "1")
  • > -> removed
  • < -> removed
  • | -> è
  • " -> ' (double to single quotes)

4.5 Customizing Character Replacements

Adding a New Replacement

Example: Replace @ with (at)

  1. For tags (Section 9, tag-level):
$set(title,$replace(%title%,@,(at)))
$set(album,$replace(%album%,@,(at)))
  1. For filenames (Section 9, filename-level):
$set(_titleForFilename,$replace(%_titleForFilename%,@,(at)))
$set(_albumForFilename,$replace(%_albumForFilename%,@,(at)))

Changing an Existing Replacement

Example: Change : replacement from _ to -

Find this line in Section 9:

$set(_titleForFilename,$replace(%_titleForFilename%,:,_))

Change to:

$set(_titleForFilename,$replace(%_titleForFilename%,:,-))

Repeat for all filename variables.

Using Regex Replacements

For more complex patterns, use $rreplace():

$set(title,$rreplace(%title%,pattern,replacement))

Example: Remove all parentheses and contents:

$set(title,$rreplace(%title%,\(.*?\),))

Example: Convert "feat. Artist" to "[Artist]":

$set(title,$rreplace(%title%, feat\. (.*), [\1]))

5. VBR Bitrate Mapping

5.1 What is VBR?

CBR (Constant Bitrate):

  • Fixed bitrate throughout the entire file
  • Example: 320 kbps CBR - every second uses exactly 320 kbit
  • File size is predictable
  • Common presets: 320, 256, 192, 128, 96, 64 kbps

VBR (Variable Bitrate):

  • Bitrate varies based on complexity of audio
  • Complex parts (loud, detailed) get higher bitrate
  • Simple parts (silence, simple tones) get lower bitrate
  • Better quality/size ratio than CBR
  • Picard reports average bitrate

How to detect: If Picard's average bitrate doesn't match a standard CBR preset (320, 256, 192, etc.), assume VBR.

5.2 Detection Logic

The script determines CBR vs VBR by checking if the bitrate matches standard presets:

Standard CBR presets: 320, 256, 224, 192, 160, 128, 112, 96, 80, 64, 48, 40, 32, 24, 16, 8

If bitrate matches -> CBR
If bitrate doesn't match -> VBR

Example:

  • Picard reports 320.0 kbps -> Exactly 320 -> CBR
  • Picard reports 245.3 kbps -> Not a standard preset -> VBR (likely V0)

5.3 LAME VBR Quality Levels

LAME is the most popular MP3 encoder and defines standard VBR presets (V0-V9).

Complete VBR Mapping Table

Bitrate Range (kbps) LAME Preset Script Label Quality Description Typical Use
339+ Custom/Extreme 320+ Extreme quality VBR Very high quality VBR
320-339 V0 alt 320 Extreme Alternative V0 extreme
260-319 Custom V0+ High+ High quality VBR+
220-260 V0 V0 Excellent (245 avg) Most popular high quality
192-220 V1 V1 Excellent (225 avg) Slightly smaller than V0
170-191 V2 V2 Transparent (190 avg) Most can't tell from original
150-170 V3 V3 Good (175 avg) Good quality, smaller size
140-150 V4 V4 Good (165 avg) Acceptable quality
130-140 V5 V5 Moderate (130 avg) Moderate quality
120-130 V6 V6 Moderate (115 avg) Smaller files
96-120 V7 V7 Acceptable Noticeably compressed
70-95 V8 V8 Low Low quality
45-69 V9 V9 Very low Very low quality
<45 N/A [actual kbps] Poor Below standard range

5.4 Filename Examples

CBR:

01. Track [320 44100KHz CBR 2ch].mp3   -> 320 kbps CBR
02. Track [192 44100KHz CBR 2ch].mp3   -> 192 kbps CBR
03. Track [128 44100KHz CBR 2ch].mp3   -> 128 kbps CBR

VBR:

01. Track [V0 44100KHz VBR 2ch].mp3    -> LAME V0 (245 avg)
02. Track [V2 44100KHz VBR 2ch].mp3    -> LAME V2 (190 avg)
03. Track [V5 44100KHz VBR 2ch].mp3    -> LAME V5 (130 avg)
04. Track [320+ 44100KHz VBR 2ch].mp3  -> VBR above 339 kbps
05. Track [71 44100KHz VBR 2ch].mp3    -> VBR outside standard range

Lossless:

01. Track [44100KHz 16bit 2ch].flac
02. Track [96000KHz 24bit 2ch].flac
03. Track [48000KHz 16bit 2ch].m4a

5.5 How the Mapping Code Works

Step 1: Extract integer bitrate

$set(_intBitRate,$rreplace(%_bitrate%,\\.\\d*\$,))

Removes decimal: 245.3 -> 245

Step 2: Check if CBR

$if($eq_any(%_intBitRate%,320,256,224,192,160,128,112,96,80,64,48,40,32,24,16,8),
    CBR...,
    VBR...
)

Step 3: If VBR, map to quality level

$if($gt(%_vbrRateValue%,339),$set(_fileVBRRate,320+),
$if($gt(%_vbrRateValue%,319),$set(_fileVBRRate,320),
$if($gt(%_vbrRateValue%,260),$set(_fileVBRRate,V0+),
$if($gt(%_vbrRateValue%,220),$set(_fileVBRRate,V0),
...

Uses nested $if() with $gt() (greater than) to find the right range.

5.6 Special Cases

320+ kbps VBR

Some extreme quality VBR encodes can average above 320 kbps (up to ~340 kbps for MP3).

Detection: Bitrate > 339 kbps Label: 320+

Example:

01. Track [320+ 44100KHz VBR 2ch].mp3

Non-Standard VBR

Files encoded with custom VBR settings outside LAME standard ranges show actual bitrate.

Example: 71 kbps average (between V9 and below standard range)

01. Track [71 44100KHz VBR 2ch].mp3

Lossless Files

FLAC, ALAC, and other lossless formats don't use CBR/VBR labels. Instead, they show file format.

Example:

FLAC 96KHz 24bit 2ch
ALAC 48KHz 16bit 2ch

6. Path Generation Examples

6.1 Example 1: Basic Artist Album (Single-Disc CD)

Configuration:

_orderTypeForRoot = 2
_orderTypeForArtist = 1
_separateByTypeInArtistDirectory = 0
_showDate = 1
_showIDNum = 1
_useSubDiscDirectory = 1

Metadata:

Artist: The Beatles
Album: Abbey Road
Year: 1969
Media: CD
Release Type: album
Total Discs: 1
Total Tracks: 17
Track 1: Come Together (4m20s)
Bitrate: 320 kbps CBR
Sample Rate: 44100 Hz
Channels: 2
MusicBrainz Album ID: 123abc
Catalog Number: XPCD-456

Path Construction (Step-by-Step):

Step 1: Root organization
  _orderTypeForRoot = 2 -> Use artist first letter
  Artist = "The Beatles"
  First letter (after removing "The") = "B"
  Result: /B/

Step 2: Artist name
  _orderTypeForArtist = 1 -> Use first name sorting
  Artist = "The Beatles"
  Sort tag = "Beatles, The"
  Result: /B/Beatles, The/

Step 3: Album type detection
  releasetype = "album" -> _isAlbum = 1
  _separateByTypeInArtistDirectory = 0 -> No type subfolder

Step 4: Album name with metadata
  Album = "Abbey Road"
  Year = 1969, _showDate = 1 -> Add (1969) before album name
  Media = "CD", Extension = "MP3" -> Add [CD - MP3]
  _showIDNum = 1 -> Add [mbid] {catalog}
  Result: /B/Beatles, The/(1969) Abbey Road [CD - MP3] [123abc] {XPCD-456}/

Step 5: Multi-disc check
  totaldiscs = 1 -> No disc subfolder needed

Step 6: Track filename
  Track 1: "Come Together"
  tracknumber = 1, totaltracks = 17 -> Pad to 2 digits: 01
  _showTime = 1 -> Add [4m20s]
  _showBandwidth = 1 -> Add [320 44100KHz CBR 2ch]
  Result: 01. Come Together [4m20s] [320 44100KHz CBR 2ch].mp3

Final Path:

/B/Beatles, The/(1969) Abbey Road [CD - MP3] [123abc] {XPCD-456}/01. Come Together [4m20s] [320 44100KHz CBR 2ch].mp3

6.2 Example 2: Multi-Disc Album with Subtitles

Configuration:

_orderTypeForRoot = 2
_orderTypeForArtist = 1
_separateByTypeInArtistDirectory = 1
_separateAlbum = 0
_useSubDiscDirectory = 1
_showDiscSubtitle = 1
_nameForTypeCD = Disc

Metadata:

Artist: Pink Floyd
Album: The Wall
Year: 1979
Media: CD
Release Type: album
Total Discs: 2
Disc 1 Subtitle: Part 1
Disc 2 Subtitle: Part 2
Disc 1, Track 1: In the Flesh? (3:19)
Disc 2, Track 1: Hey You (4:42)

Path Construction:

Step 1: Root organization
  Artist first letter = "P"
  Result: /P/

Step 2: Artist name
  Artist = "Pink Floyd"
  Result: /P/Pink Floyd/

Step 3: Album type subfolder
  _isAlbum = 1, _separateByTypeInArtistDirectory = 1
  _separateAlbum = 0 -> No Albums/ subfolder for standard albums
  Result: /P/Pink Floyd/

Step 4: Album name
  Album = "The Wall"
  Year = 1979 -> Add (1979) before album name
  Media = "CD", Extension = "FLAC" -> Add [CD - FLAC]
  Result: /P/Pink Floyd/(1979) The Wall [CD - FLAC]/

Step 5: Disc subfolders
  totaldiscs = 2 -> Multi-disc
  _useSubDiscDirectory = 1 -> Create disc subfolders
  _showDiscSubtitle = 1 -> Include disc subtitles
  Disc 1: Disc01 - Part 1/
  Disc 2: Disc02 - Part 2/

Step 6: Track filenames
  Disc 1, Track 1: "In the Flesh?"
  tracknumber = 1 -> 01
  Result: 01. In the FleshG [3m19s] [96000KHz 16bit 2ch].flac
  (Note: "?" replaced with "G")

Final Paths:

/P/Pink Floyd/(1979) The Wall [CD - FLAC]/Disc01 - Part 1/01. In the FleshG [3m19s] [96000KHz 16bit 2ch].flac
/P/Pink Floyd/(1979) The Wall [CD - FLAC]/Disc02 - Part 2/01. Hey You [4m42s] [96000KHz 16bit 2ch].flac

6.3 Example 3: Vinyl with MusicBrainz Track Numbering

Configuration:

_orderTypeForRoot = 2
_orderTypeForArtist = 2
_separateByTypeInArtistDirectory = 1
_useMusicBrainzStyleForVinylTrack = 1
_nameForTypeVinyl = Side

Metadata:

Artist: David Bowie
Artist Sort: Bowie, David
Album: The Rise and Fall of Ziggy Stardust and the Spiders from Mars
Year: 1972
Media: Vinyl
Release Type: album
Total Discs: 2 (sides)
Side A, Track 1: Five Years (4:43, MB track: A1)
Side A, Track 2: Soul Love (3:35, MB track: A2)
Side B, Track 1: Lady Stardust (3:22, MB track: B1)

Path Construction:

Step 1: Root organization
  Artist sort = "Bowie, David"
  First letter of last name = "B"
  Result: /B/

Step 2: Artist name
  _orderTypeForArtist = 2 -> Use last name sorting
  Artist sort = "Bowie, David"
  Result: /B/Bowie, David/

Step 3: Album type subfolder
  _separateByTypeInArtistDirectory = 1, _isAlbum = 1
  Result: /B/Bowie, David/

Step 4: Album name
  Album = "The Rise and Fall of Ziggy Stardust and the Spiders from Mars"
  (Truncated if > 65 chars)
  Year = 1972 -> Add (1972)
  Media = "Vinyl" -> Add [Vinyl]
  Result: /B/Bowie, David/(1972) The Rise and Fall of Ziggy Stardust... [Vinyl - MP3]/

Step 5: Side subfolders
  Media = "Vinyl", totaldiscs = 2
  _nameForTypeVinyl = "Side"
  Side 1: Side 1/
  Side 2: Side 2/

Step 6: Track filenames (Vinyl style)
  _useMusicBrainzStyleForVinylTrack = 1
  Media = "Vinyl" -> Use MB track numbers
  Side 1, Track 1: MB track = "A1"
  Result: A1. Five Years [4m43s] [V0 44100KHz VBR 2ch].mp3

Final Paths:

/B/Bowie, David/(1972) The Rise and Fall of Ziggy Stardust... [Vinyl - MP3]/Side 1/A1. Five Years [4m43s] [V0 44100KHz VBR 2ch].mp3
/B/Bowie, David/(1972) The Rise and Fall of Ziggy Stardust... [Vinyl - MP3]/Side 1/A2. Soul Love [3m35s] [V0 44100KHz VBR 2ch].mp3
/B/Bowie, David/(1972) The Rise and Fall of Ziggy Stardust... [Vinyl - MP3]/Side 2/B1. Lady Stardust [3m22s] [V0 44100KHz VBR 2ch].mp3

6.4 Example 4: Various Artists Compilation

Configuration:

_variousArtistsDirectory = Various/
_useSubDiscDirectory = 1

Metadata:

Album Artist: Various Artists
Album: Now That's What I Call Music! 80
Year: 2011
Media: CD
Release Type: album + compilation
Total Discs: 2
Disc 1, Track 1: Somebody That I Used to Know - Gotye feat. Kimbra (4:04)
Disc 1, Track 2: We Found Love - Rihanna feat. Calvin Harris (3:35)
Disc 2, Track 1: Party Rock Anthem - LMFAO (4:23)

Path Construction:

Step 1: Detect Various Artists
  Album Artist = "Various Artists" -> _isVarious = 1

Step 2: Route to Various Artists directory
  _variousArtistsDirectory = "Various/"
  Album first letter = "N"
  Result: /Various/N/

Step 3: Album name
  Album = "Now That's What I Call Music! 80"
  Year = 2011 -> Add (2011) before album name
  Media = "CD", Extension = "MP3" -> Add [CD - MP3]
  Result: /Various/N/(2011) Now That's What I Call Music! 80 [CD - MP3]/

Step 4: Disc subfolders
  totaldiscs = 2 -> Multi-disc
  Result: Disc01/, Disc02/

Step 5: Track filenames
  Track 1, Disc 1:
  Title = "Somebody That I Used to Know"
  Featured artists detected -> Add [Gotye feat. Kimbra]
  Result: 01. Somebody That I Used to Know [Gotye feat. Kimbra] [4m04s].mp3

Final Paths:

/Various/N/(2011) Now That's What I Call Music! 80 [CD - MP3]/Disc01/01. Somebody That I Used to Know [Gotye feat. Kimbra] [4m04s].mp3
/Various/N/(2011) Now That's What I Call Music! 80 [CD - MP3]/Disc01/02. We Found Love [Rihanna feat. Calvin Harris] [3m35s].mp3
/Various/N/(2011) Now That's What I Call Music! 80 [CD - MP3]/Disc02/01. Party Rock Anthem [LMFAO] [4m23s].mp3

6.5 Example 5: Album with Type Separation

Configuration:

_orderTypeForRoot = 2
_orderTypeForArtist = 1
_separateByTypeInArtistDirectory = 1
_separateAlbum = 0
_singlesSubDirectory = Singles/
_liveSubDirectory = Live/

Metadata (3 releases):

Album:

Artist: Nirvana
Album: Nevermind
Year: 1991
Release Type: album

Single:

Artist: Nirvana
Album: Smells Like Teen Spirit
Year: 1991
Release Type: single

Live:

Artist: Nirvana
Album: MTV Unplugged in New York
Year: 1994
Release Type: album + live

Path Construction:

All releases:
  Root: /N/Nirvana/

Album (Nevermind):
  _isAlbum = 1, _separateAlbum = 0 -> No Albums/ subfolder
  Result: /N/Nirvana/(1991) Nevermind [CD - MP3]/

Single (Smells Like Teen Spirit):
  _isSingle = 1 -> Use Singles/ subfolder
  Result: /N/Nirvana/Singles/(1991) Smells Like Teen Spirit [CD - MP3]/

Live (MTV Unplugged):
  _isLive = 1 -> Use Live/ subfolder
  Result: /N/Nirvana/Live/(1994) MTV Unplugged in New York [CD - MP3]/

Final Paths:

/N/Nirvana/(1991) Nevermind [CD - MP3]/01. Smells Like Teen Spirit.mp3
/N/Nirvana/Singles/(1991) Smells Like Teen Spirit [CD - MP3]/01. Smells Like Teen Spirit.mp3
/N/Nirvana/Live/(1994) MTV Unplugged in New York [CD - MP3]/01. About a Girl.mp3

6.6 Example 6: Tribute Album with Original Artist Routing

Configuration:

_altArtistSort = 1
_tributeSubDirectory = Tribute/

Metadata:

Album Artist: Various Artists
Album: We Will Rock You - Queen Tribute
Year: 2005
Release Type: album + compilation
Custom Tag: coverTributeSort = Tribute
Custom Tag: albumartistsort = Queen
Track 1: We Will Rock You - Five (2:58)

Path Construction:

Step 1: Detect tribute album
  coverTributeSort = "Tribute" -> _isTribute = 1
  _altArtistSort = 1 -> Route to original artist

Step 2: Use custom albumartistsort
  albumartistsort = "Queen"
  First letter = "Q"
  Result: /Q/Queen/

Step 3: Tribute subfolder
  _isTribute = 1 -> Use Tribute/ subfolder
  Result: /Q/Queen/Tribute/

Step 4: Album name
  Album = "We Will Rock You - Queen Tribute"
  Year = 2005 -> Add (2005) before album name
  Result: /Q/Queen/Tribute/(2005) We Will Rock You - Queen Tribute [CD - MP3]/

Step 5: Track filename
  Track 1: "We Will Rock You"
  Track artist = "Five" (different from album artist)
  -> Add [Five]
  Result: 01. We Will Rock You [Five] [2m58s].mp3

Final Path:

/Q/Queen/Tribute/(2005) We Will Rock You - Queen Tribute [CD - MP3]/01. We Will Rock You [Five] [2m58s].mp3

Note: This requires manually setting two custom tags: coverTributeSort = Tribute and albumartistsort = Queen.


6.7 Example 7: Genre Pre-Sort (Classical)

Configuration:

_isSubSort = 1
_subSortClassical = Classical/
_orderTypeForRoot = 2
_orderTypeForArtist = 2

Metadata:

Artist: Johann Sebastian Bach
Artist Sort: Bach, Johann Sebastian
Album: Brandenburg Concertos
Year: 1721
Custom Tag: genresort = Classical

Path Construction:

Step 1: Detect genre subsort
  genresort = "Classical"
  -> Triggers: _subSortDirectory = "Classical/"

Step 2: Genre subsort folder
  Result: /Classical/

Step 3: Artist first letter (last name)
  Artist Sort = "Bach, Johann Sebastian"
  First letter of last name = "B"
  Result: /Classical/B/

Step 4: Artist name
  _orderTypeForArtist = 2 -> Use sort name
  Artist Sort = "Bach, Johann Sebastian"
  Result: /Classical/B/Bach, Johann Sebastian/

Step 5: Album name
  Album = "Brandenburg Concertos"
  Year = 1721 -> Add (1721) before album name
  Result: /Classical/B/Bach, Johann Sebastian/(1721) Brandenburg Concertos [CD - FLAC]/

Final Path:

/Classical/B/Bach, Johann Sebastian/(1721) Brandenburg Concertos [CD - FLAC]/01. Concerto No. 1 in F Major.flac

6.8 Example 8: Soundtrack

Configuration:

_soundTracksDirectory = Soundtrack/

Metadata:

Album: Guardians of the Galaxy - Awesome Mix Vol. 1
Year: 2014
Release Type: soundtrack
Track 1: Hooked on a Feeling - Blue Swede (2:53)

Path Construction:

Step 1: Detect soundtrack
  releasetype = "soundtrack" -> _isSoundTrack = 1

Step 2: Route to Soundtrack directory
  _soundTracksDirectory = "Soundtrack/"
  Album first letter = "G"
  Result: /Soundtrack/G/

Step 3: Album name
  Album = "Guardians of the Galaxy - Awesome Mix Vol. 1"
  Year = 2014 -> Add (2014) before album name
  Result: /Soundtrack/G/(2014) Guardians of the Galaxy - Awesome Mix Vol. 1 [CD - MP3]/

Step 4: Track filename
  Track 1: "Hooked on a Feeling"
  Track artist = "Blue Swede" (soundtrack, show artist)
  -> Add [Blue Swede]
  Result: 01. Hooked on a Feeling [Blue Swede] [2m53s].mp3

Final Path:

/Soundtrack/G/(2014) Guardians of the Galaxy - Awesome Mix Vol. 1 [CD - MP3]/01. Hooked on a Feeling [Blue Swede] [2m53s].mp3

6.9 Example 9: Incomplete Album

Configuration:

_earlierPresortForIncompletes = 1
_incompleteDirectory = Partial

Metadata:

Artist: Radiohead
Album: OK Computer
Year: 1997
Total Tracks: 12
Matched Tracks: 8
Complete: No

Path Construction:

Step 1: Detect incomplete
  $is_complete() = false -> _isIncomplete = 1

Step 2: Early presort
  _earlierPresortForIncompletes = 1
  -> Add "- Partial" prefix
  Result: /- Partial/

Step 3: Standard artist organization
  Artist first letter = "R"
  Result: /- Partial/R/Radiohead/

Step 4: Album name
  Album = "OK Computer"
  Year = 1997 -> Add (1997) before album name
  Result: /- Partial/R/Radiohead/(1997) OK Computer [CD - MP3]/

Final Path:

/- Partial/R/Radiohead/(1997) OK Computer [CD - MP3]/01. Airbag.mp3
/- Partial/R/Radiohead/(1997) OK Computer [CD - MP3]/03. Subterranean Homesick Alien.mp3
...
(tracks 2, 4, 6, 7, 9-12 missing)

Override: Set custom tag SavePerfectAnyway = yes to skip the "- Partial" prefix.


6.10 Example 10: EP with Bitrate Display

Configuration:

_separateByTypeInArtistDirectory = 1
_epSubDirectory = EP/
_showBandwidth = 1

Metadata:

Artist: The xx
Album: Fantasy EP
Year: 2009
Release Type: ep
Track 1: Fantasy (3:41, VBR 245 kbps avg)
Track 2: Teardrops (5:12, VBR 238 kbps avg)

Path Construction:

Step 1: Standard artist organization
  Artist first letter = "X"
  Result: /X/xx, The/

Step 2: EP subfolder
  _isEP = 1 -> Use EP/ subfolder
  Result: /X/xx, The/EP/

Step 3: Album name
  Album = "Fantasy EP"
  Year = 2009 -> Add (2009) before album name
  Result: /X/xx, The/EP/(2009) Fantasy EP [CD - MP3]/

Step 4: Track filenames with VBR detection
  Track 1: VBR 245 kbps -> Maps to V0
  _showBandwidth = 1 -> Add [V0 44100KHz VBR 2ch]
  Result: 01. Fantasy [3m41s] [V0 44100KHz VBR 2ch].mp3

  Track 2: VBR 238 kbps -> Maps to V0
  Result: 02. Teardrops [5m12s] [V0 44100KHz VBR 2ch].mp3

Final Paths:

/X/xx, The/EP/(2009) Fantasy EP [CD - MP3]/01. Fantasy [3m41s] [V0 44100KHz VBR 2ch].mp3
/X/xx, The/EP/(2009) Fantasy EP [CD - MP3]/02. Teardrops [5m12s] [V0 44100KHz VBR 2ch].mp3

7. Advanced Features

7.1 Genre-Based Sorting

(See Section 3.6 - Genre SubSort)

7.2 Tribute and Cover Album Handling

Overview

The tribute/cover feature allows you to file tribute and cover albums under the original artist being tributed or covered, rather than under the performing artist.

Use case: You want "A Tribute to Queen" by Various Artists filed under Queen, not Various Artists.

Requirements

This feature requires manually setting two custom tags:

  1. coverTributeSort - Set to "Tribute" or "Cover"
  2. albumartistsort - Set to the original artist name

Why manual? MusicBrainz doesn't have a standard "this is a tribute album" field, so we use custom tags.

How to Set Custom Tags in Picard

  1. Select the album in Picard
  2. Right-click -> Tags from file names or Edit Tags
  3. Add a new tag:
    • Tag name: coverTributeSort
    • Value: Tribute (or Cover)
  4. Add another tag:
    • Tag name: albumartistsort
    • Value: Original artist name (e.g., "Queen")
  5. Save the file

Configuration

_altArtistSort = 1    # Enable tribute/cover routing (default)

Example Workflow

Album: "We Will Rock You - Queen Tribute" by Various Artists

Step 1: Tag the album

coverTributeSort = Tribute
albumartistsort = Queen

Step 2: Script detects

$if($in(%coverTributeSort%,Tribute),$set(_isTribute,1))

Step 3: Routes to original artist

$if($eq_all(%coverTributeSort%,%_altArtistSort%,%_isTribute%,1),
  $if2(%_artistSort%,%_albumartistForFilename%,%_artistForFilename%)
)/

Uses albumartistsort = Queen for the folder.

Result:

/Q/Queen/Tribute/(2005) We Will Rock You - Queen Tribute [CD - MP3]/

Cover Albums

Same process, but use coverTributeSort = Cover:

Example: "Devolution" by DEVO (covers)

Tags:

coverTributeSort = Cover
albumartistsort = [Original Artist]

Result:

/D/DEVO/Cover/(2010) Devolution [CD - MP3]/

Limitations

  • Must manually tag each tribute/cover album
  • MusicBrainz doesn't provide this automatically
  • albumartistsort must be spelled exactly as you want the folder named

7.3 DevMode (Development/Testing)

Purpose

DevMode allows you to test the script's audio metrics detection without actual music files.

Use case:

  • Testing VBR mapping logic
  • Debugging bitrate detection
  • Verifying path generation

Configuration

_devMode = 1    # Enable test mode

WARNING: Must be set to 0 for actual use!

Test Values

When _devMode = 1, the script uses these hardcoded values instead of real file metadata:

Bitrate: 71.426 kbps (VBR V8 range)
Sample Rate: 44100 Hz
Bit Depth: 16 bit
Channels: 2
Title: "My Great Score"

What DevMode Does

  1. Bitrate Detection:

    $if($eq(%_devMode%,1),
      $set(_biitrate,71.426),      # Use test bitrate
      $set(_intBitRate,$rreplace(%_bitrate%,\\.\\d*\$,))  # Use real bitrate
    )
    
  2. Audio Metrics:

    $if($eq(%_devMode%,1),
      $set(_bitRateSpeed,%_saample_rate%KHz),    # Test sample rate
      $set(_bitRateSpeed,%_sample_rate%KHz)      # Real sample rate
    )
    
  3. Title:

    $if($eq(%_devMode%,1),
      $set(_titleForFilename,%_tiitle%),         # Test title
      $set(_titleForFilename,%_titleForFilename%) # Real title
    )
    

Expected Output (DevMode = 1)

All files will use test values:

01. My Great Score [Xm##s] [V8 44100KHz VBR 2ch].mp3

Bitrate 71.426 maps to V8.

How to Test

  1. Set _devMode = 1 in configuration
  2. Copy script to Picard
  3. Tag any file
  4. Check filename - should show test values
  5. IMPORTANT: Set _devMode = 0 before actual use!

7.4 Custom Tag Integration

The script supports several custom tags you can set manually for special handling.

SavePerfectAnyway

Purpose: Override incomplete album detection.

Values: yes (any other value = not set)

Use case: You have a complete album but Picard thinks it's incomplete (e.g., you removed tracks intentionally).

How to set:

  1. Right-click file -> Edit Tags
  2. Add tag: SavePerfectAnyway = yes
  3. Save

Effect:

Normal: /- Partial/Artist/Album/
With tag: /Artist/Album/

SaveIncompleteAnyway

Purpose: Force incomplete album to go to incomplete directory.

Values: yes

Use case: Opposite of above - force incomplete routing.

Effect:

$if($in(%SaveIncompleteAnyway%,yes),%_incompleteDirectory%)/

BitRateSplit

Purpose: Add bitrate to album folder name.

Values: Yes

Configuration: (Not in default script, must add manually)

Example modification:

$if($in(%BitRateSplit%,Yes), %_fileVBRRate%%_fileCBRRate% %_bitRateType%)

Result:

/Artist/(1985) Album [320 CBR] [CD - MP3]/

coverTributeSort

(See Section 7.2 - Tribute and Cover Albums)

genresort

(See Section 3.6 - Genre SubSort)


8. Variables Reference

8.1 MusicBrainz Standard Tags

These tags come from MusicBrainz or existing file metadata:

Tag Description Example
%artist% Track artist name "The Beatles"
%albumartist% Album artist name "The Beatles"
%album% Album title "Abbey Road"
%title% Track title "Come Together"
%date% Release date "1969-09-26"
%originaldate% Original release date "1969-09-26"
%originalyear% Original release year "1969"
%tracknumber% Track number "1"
%totaltracks% Total tracks on disc "17"
%discnumber% Disc number "1"
%totaldiscs% Total discs in release "2"
%discsubtitle% Disc subtitle "Acoustic"
%media% Media type "CD", "Vinyl", "Digital Media"
%label% Record label "Apple Records"
%catalognumber% Catalog number "XPCD-123"
%releasetype% Release type(s) "album", "single", "live"
%releasestatus% Release status "Official", "Promotion"
%_releasecomment% Disambiguation comment "Blue Album"
%musicbrainz_albumid% MusicBrainz Album ID "abc123..."
%musicbrainz_albumartistid% MusicBrainz Album Artist ID "def456..."
%_musicbrainz_tracknumber% MusicBrainz track number "A1", "B2" (vinyl)
%genre% Genre "Rock"
%albumgrouping% Album grouping "Rock", "Pop" (Last.fm)
%compilation% Compilation flag "1" if compilation
%_length% Track length "4:20"
%_bitrate% Average bitrate "320.0", "245.3"
%_sample_rate% Sample rate "44100"
%_bits_per_sample% Bit depth "16", "24"
%_channels% Number of channels "2", "6"
%_extension% File extension "mp3", "flac"
%_filename% Original filename "track01"

8.2 Additional Artists Variables Plugin Tags

These tags require the "Additional Artists Variables" plugin:

Album Variables

Tag Description
%_artists_album_primary_id% ID of primary album artist
%_artists_album_primary_std% Primary album artist [standardized]
%_artists_album_primary_cred% Primary album artist [as credited]
%_artists_album_primary_sort% Primary album artist [sort name]
%_artists_album_additional_id% IDs of additional album artists
%_artists_album_additional_std% Additional album artists [standardized]
%_artists_album_additional_cred% Additional album artists [as credited]
%_artists_album_all_std% All album artists [standardized]
%_artists_album_all_cred% All album artists [as credited]
%_artists_album_all_sort% All album artists [sort names]
%_artists_album_all_sort_primary% Primary [sort] + additional [std]
%_artists_album_all_count% Number of album artists

Track Variables

Tag Description
%_artists_track_primary_id% ID of primary track artist
%_artists_track_primary_std% Primary track artist [standardized]
%_artists_track_primary_cred% Primary track artist [as credited]
%_artists_track_primary_sort% Primary track artist [sort name]
%_artists_track_additional_id% IDs of additional track artists
%_artists_track_additional_std% Additional track artists [standardized]
%_artists_track_additional_cred% Additional track artists [as credited]
%_artists_track_all_std% All track artists [standardized]
%_artists_track_all_cred% All track artists [as credited]
%_artists_track_all_sort% All track artists [sort names]
%_artists_track_all_sort_primary% Primary [sort] + additional [std]
%_artists_track_all_count% Number of track artists

What does [standardized] vs [as credited] mean?

  • Standardized: Official artist name from MusicBrainz database
  • As credited: How the artist is credited on this specific release
  • Sort: Name formatted for sorting (e.g., "Beatles, The")

Example:

Artist credited as: "Weird Al"
Standardized name: "Weird Al Yankovic"
Sort name: "Yankovic, Weird Al"

8.3 Script Internal Variables

Variables created and used by the script (all start with _):

Constants (Section 1)

Variable Value Description
%_cUnknownArtistID% 125ec42a-... MusicBrainz Unknown Artist ID
%_cVariousArtistID% 89ad4ac3-... MusicBrainz Various Artists ID
%_cUnknownArtist% [Unknown Artist] Display name for unknown artist
%_cVariousArtist% [Various Artists] Display name for various artists
%_cUnknownAlbum% [Unknown Album] Display name for unknown album
%_cNoTitle% [Unknown Title] Display name for unknown title
%_cClassical% [Classical] Classical music folder name
%_cSoundtrack% [Soundtracks] Soundtrack folder name
%_cSingles% [~Singles~] Singles folder name
%_cOther% [Other] Other releases folder name

Working Variables (Section 4)

Variable Description
%_nMedia% Media type
%_nTotalDiscs% Total discs
%_nDiscNum% Disc number
%_nTotalTracks% Total tracks
%_nTrackNum% Track number
%_nAlbumArtistID% Album artist ID
%_nInitial% Artist initial folder (e.g., "~ B ~/")
%_nFeat% Featured artist string
%_PaddedDiscNum% Padded disc number
%_PaddedTrackNum% Padded track number
%_nYear% Year in [YYYY] format
%_nTNum% Complete track number (disc+track)

Filename Variables (Section 8)

Variable Description
%_titleForFilename% Sanitized track title
%_albumForFilename% Sanitized album title
%_discsubtitleForFilename% Sanitized disc subtitle
%_albumartistForFilename% Sanitized album artist
%_artistForFilename% Sanitized track artist
%_albumartistsortForFilename% Sanitized album artist sort
%_artistsortForFilename% Sanitized track artist sort

Audio Metrics Variables (Section 10)

Variable Description
%_intBitRate% Integer bitrate value
%_bitRateSpeed% Sample rate (e.g., "44100KHz")
%_bitsPerSample% Bit depth
%_audioChannels% Channel count
%_bitRateType% "CBR" or "VBR"
%_cbrRateValue% CBR bitrate value
%_vbrRateValue% VBR bitrate value
%_fileCBRRate% CBR label for filename
%_fileVBRRate% VBR label for filename (V0, V2, etc.)

Detection Flags (Section 6)

Variable Value Description
%_isAlbum% 1 if album Is this an album release?
%_isSingle% 1 if single Is this a single?
%_isLive% 1 if live Is this a live recording?
%_isEP% 1 if EP Is this an EP?
%_isBroadcast% 1 if broadcast Is this a broadcast?
%_isInterview% 1 if interview Is this an interview?
%_isArtistCompil% 1 if artist compilation Artist compilation?
%_isAudiobook% 1 if audiobook Is this an audiobook?
%_isOther% 1 if other Is this "other" type?
%_isTribute% 1 if tribute Is this a tribute album?
%_isCover% 1 if cover Is this a cover album?
%_isPodcast% 1 if podcast Is this a podcast?
%_isSoundTrack% 1 if soundtrack Is this a soundtrack?
%_isIncomplete% 1 if incomplete Is the album incomplete?
%_isVideo% 1 if video Is this a video?
%_isVarious% 1 if various Is album artist "Various Artists"?
%_isGlobalCompil% 1 if compilation Is compilation flag set?

9. Customization Guide

9.1 Adding New Character Replacements

Scenario: You want to replace @ with (at) in filenames.

Step 1: Decide scope (tags or filenames)

For filenames only, go to Section 9, filename-level replacements.

Step 2: Add replacement

Find the filename replacement block:

$noop( Character Replacements )
$set(_titleForFilename,$replace(%_titleForFilename%,:,_))
$set(_albumForFilename,$replace(%_albumForFilename%,:,_))
...

Step 3: Add your new line

$set(_titleForFilename,$replace(%_titleForFilename%,@,(at)))
$set(_albumForFilename,$replace(%_albumForFilename%,@,(at)))
$set(_artistForFilename,$replace(%_artistForFilename%,@,(at)))

Result:

Track: "Email @ Night"
Filename: "01. Email (at) Night.mp3"

9.2 Creating New Genre Subsort Categories

Scenario: You want to add a "Soundtrack - Games" category for video game soundtracks.

Step 1: Define folder name (Section 2.8)

$set(_subSortGameSoundtrack,Soundtrack - Games/)

Step 2: Add detection logic (Section 11)

Find the genre subsort detection block:

$if($in(%genresort%,Classical),$set(_subSortDirectory,%_subSortClassical%))
$if($in(%genresort%,Jazz),$set(_subSortDirectory,%_subSortJazz%))
...

Add your new line:

$if($in(%genresort%,Game Soundtrack),$set(_subSortDirectory,%_subSortGameSoundtrack%))

Step 3: Tag your files

Add custom tag genresort = Game Soundtrack to your video game soundtracks.

Result:

/Soundtrack - Games/Artist/Album/

9.3 Modifying Path Structure

Example 1: Remove Year from Album Folder

Find:

$if($eq(%_showDate%,1),$if($if2(%originalyear%,%originaldate%,%date%), \($left($if2(%originalyear%,%originaldate%,%date%),4)\) ,))

Change to:

$noop( Year display disabled )

Or simply set:

_showDate = 0

Example 2: Change Artist Letter Folder Format

Current: /B/Artist/ Want: /Artists-B/Artist/

Find (Section 11):

$if($eq(%_orderTypeForRoot%,2),
  $upper($firstalphachar($if2(%_albumartistForFilename%,%_artistForFilename%),#1))
)/

Change to:

$if($eq(%_orderTypeForRoot%,2),
  Artists-$upper($firstalphachar($if2(%_albumartistForFilename%,%_artistForFilename%),#1))
)/

Result: /Artists-B/Beatles, The/Album/

Example 3: Add Custom Prefix to All Paths

Want: /Music/ prefix before everything

Find (Section 11, start of path generation):

$noop( Step 1: Root Level File Type Separation )
$if($eq(%_rootLevelTypeSeparation%,1),$upper(%_extension%),)

Change to:

$noop( Step 0: Custom prefix )
Music/

$noop( Step 1: Root Level File Type Separation )
$if($eq(%_rootLevelTypeSeparation%,1),$upper(%_extension%),)

Result: /Music/B/Beatles, The/Album/

9.4 Adjusting Filename Format

Example 1: Remove Audio Quality from Filename

Find (Section 12):

$if($eq(%_quickNoNameFormat%,0),$if($eq(%_showBandwidth%,1),[%_fileCBRRate%%_fileVBRRate% %_bitRateSpeed% %_bitRateType% %_audioChannels%]))

Change to:

$noop( Audio quality display disabled )

Or simply set:

_showBandwidth = 0

Example 2: Change Track Number Format

Current: 01. Track Want: 01 - Track

Find (Section 12):

$if(%tracknumber%,...$num(%tracknumber%,2). ))

Change to:

$if(%tracknumber%,...$num(%tracknumber%,2) - ))

Result: 01 - Come Together [4m20s].mp3

Example 3: Add File Size to Filename

Want: Show file size in MB

Add before filename (Section 12):

[$div(%_filesize%,1048576)MB]

Result: 01. Track [23MB] [320 44100KHz CBR 2ch].mp3

9.5 Adding New Metadata to Filenames

Example: Add Composer to Classical Music

Step 1: Check if tag exists

Picard provides %composer% tag.

Step 2: Add to filename (Section 12)

$noop( Track Title )
$if(%composer%,%composer% - )%_titleForFilename%

Result: 01. Bach - Brandenburg Concerto No. 1.flac

Example: Add BPM to Filename

Step 1: Picard provides %bpm% tag

Step 2: Add to filename

$if(%bpm%, [%bpm%BPM])

Result: 01. Track [120BPM] [320 44100KHz CBR 2ch].mp3


Appendix: Quick Reference

Common Picard Functions

Function Description Example
$set(var,value) Set variable $set(_x,hello)
$if(cond,then,else) Conditional $if(%artist%,yes,no)
$if2(a,b,c) First non-empty $if2(%artist%,Unknown)
$noop(...) No operation (comment) $noop( Comment )
$upper(text) Uppercase $upper(hello) -> HELLO
$lower(text) Lowercase $lower(HELLO) -> hello
$left(text,n) First n chars $left(Beatles,4) -> Beat
$right(text,n) Last n chars $right(Beatles,4) -> tles
$len(text) Length $len(Hello) -> 5
$replace(text,old,new) Replace string $replace(A:B,:,_) -> A_B
$rreplace(text,regex,new) Replace regex $rreplace(A123B,\\d+,X) -> AXB
$num(n,len) Pad number $num(5,3) -> 005
$gt(a,b) Greater than $gt(10,5) -> 1 (true)
$lt(a,b) Less than $lt(5,10) -> 1 (true)
$eq(a,b) Equals $eq(hello,hello) -> 1
$ne(a,b) Not equals $ne(a,b) -> 1 (true)
$in(text,search) Contains $in(hello,ll) -> 1
$trim(text) Remove whitespace $trim( hi ) -> hi
$firstalphachar(text,def) First letter $firstalphachar(Beatles,#) -> B

Configuration Quick Settings

Basic Setup:

_orderTypeForRoot = 2
_orderTypeForArtist = 1
_separateByTypeInArtistDirectory = 1
_showDate = 1

Minimal Filename:

_showTime = 0
_showBandwidth = 0
_showIDNum = 0

Multi-Disc (Merged):

_useSubDiscDirectory = 0
_mergeDiscWhenNotUsingSubDirectory = 1

No Type Separation:

_separateByTypeInArtistDirectory = 0