Create RDP Profiles on Desktop with Custom Icons

🧩 Syntax:
# Define directories
$remoteAppProfilesFolder = "C:\RemoteAppProfiles"
$iconDirectory = "C:\RemoteAppProfiles\Icons"
$logDirectory = "C:\Temp\Logs"

# Base64 strings for icons - replace these with actual base64 encoded icon data
$base64StringIcon1 = "base64string_for_icon1" # Placeholder for first .ico base64
$base64StringIcon2 = "base64string_for_icon2" # Placeholder for second .ico base64

# Ensure necessary directories exist
function CheckCreateDirectory {
    param([string]$Path)
    if (-not (Test-Path -Path $Path)) {
        New-Item -Path $Path -ItemType Directory | Out-Null
        Write-Host "Created directory: $Path"
        Write-DebugLog "Created directory: $Path"
    }
}

function Write-DebugLog {
    param([string]$Message)
    $timestamp = Get-Date -Format "yyyy-MM-dd HH:mm:ss"
    $logMessage = "${timestamp}: ${Message}"
    $logMessage | Out-File -FilePath "${logDirectory}\debug.log" -Append
    Write-Host $logMessage
}

function ConvertBase64ToIcon {
    param([string]$base64, [string]$outputPath)
    try {
        $bytes = [Convert]::FromBase64String($base64)
        [System.IO.File]::WriteAllBytes($outputPath, $bytes)
        Write-DebugLog "Icon created at $outputPath"
    } catch {
        Write-Host "Error converting base64 to icon: $_"
        Write-DebugLog "Error converting base64 to icon: $_"
    }
}

# Create logs and icons directories
CheckCreateDirectory -Path $logDirectory
CheckCreateDirectory -Path $iconDirectory
CheckCreateDirectory -Path $remoteAppProfilesFolder

# Convert base64 strings to .ico files and save them in the icons directory
$iconPaths = @()
$iconPaths += Join-Path -Path $iconDirectory -ChildPath "rdp-ico-1.ico"
$iconPaths += Join-Path -Path $iconDirectory -ChildPath "rdp-ico-2.ico"

ConvertBase64ToIcon -base64 $base64StringIcon1 -outputPath $iconPaths[0]
ConvertBase64ToIcon -base64 $base64StringIcon2 -outputPath $iconPaths[1]

# RDP Profiles
$rdpProfiles = @(
    @{
        Name                 = "RDP Profile 1 Name"
        IconPath             = $iconPaths[0]
        ConfigurationContent = @"
screen mode id:i:1
use multimon:i:1
desktopwidth:i:1920
desktopheight:i:1080
session bpp:i:32
winposstr:s:0,1,260,26,1578,1032
compression:i:1
keyboardhook:i:2
audiocapturemode:i:0
videoplaybackmode:i:1
connection type:i:7
networkautodetect:i:1
bandwidthautodetect:i:1
displayconnectionbar:i:1
enableworkspacereconnect:i:0
disable wallpaper:i:0
allow font smoothing:i:0
allow desktop composition:i:0
disable full window drag:i:1
disable menu anims:i:1
disable themes:i:0
disable cursor setting:i:0
bitmapcachepersistenable:i:1
full address:s:127.0.0.1
audiomode:i:0
redirectprinters:i:1
redirectcomports:i:1
redirectsmartcards:i:1
redirectclipboard:i:1
redirectposdevices:i:0
autoreconnection enabled:i:1
authentication level:i:2
prompt for credentials:i:1
negotiate security layer:i:1
remoteapplicationmode:i:1
alternate shell:s:
shell working directory:s:
gatewayhostname:s:
gatewayusagemethod:i:4
gatewaycredentialssource:i:4
gatewayprofileusagemethod:i:0
promptcredentialonce:i:0
gatewaybrokeringtype:i:0
use redirection server name:i:0
rdgiskdcproxy:i:0
kdcproxyname:s:
drivestoredirect:s:*
redirectlocation:i:1
smart sizing:i:1
redirectwebauthn:i:1
enablerdsaadauth:i:0
camerastoredirect:s:*
devicestoredirect:s:*
remoteapplicationname:s:RemoteApp Name 1
remoteapplicationprogram:s:C:\RemoteAppDirectory1
remoteapplicationcmdline:s:
remoteapplicationicon:s:
"@
    },
    @{
        Name                 = "RDP Profile Name"
        IconPath             = $iconPaths[1]
        ConfigurationContent = @"
screen mode id:i:1
use multimon:i:1
desktopwidth:i:1920
desktopheight:i:1080
session bpp:i:32
winposstr:s:0,1,260,26,1578,1032
compression:i:1
keyboardhook:i:2
audiocapturemode:i:0
videoplaybackmode:i:1
connection type:i:7
networkautodetect:i:1
bandwidthautodetect:i:1
displayconnectionbar:i:1
enableworkspacereconnect:i:0
disable wallpaper:i:0
allow font smoothing:i:0
allow desktop composition:i:0
disable full window drag:i:1
disable menu anims:i:1
disable themes:i:0
disable cursor setting:i:0
bitmapcachepersistenable:i:1
full address:s:127.0.0.1
audiomode:i:0
redirectprinters:i:1
redirectcomports:i:1
redirectsmartcards:i:1
redirectclipboard:i:1
redirectposdevices:i:0
autoreconnection enabled:i:1
authentication level:i:2
prompt for credentials:i:1
negotiate security layer:i:1
remoteapplicationmode:i:1
alternate shell:s:
shell working directory:s:
gatewayhostname:s:
gatewayusagemethod:i:4
gatewaycredentialssource:i:4
gatewayprofileusagemethod:i:0
promptcredentialonce:i:0
gatewaybrokeringtype:i:0
use redirection server name:i:0
rdgiskdcproxy:i:0
kdcproxyname:s:
drivestoredirect:s:*
redirectlocation:i:1
smart sizing:i:1
redirectwebauthn:i:1
enablerdsaadauth:i:0
camerastoredirect:s:*
devicestoredirect:s:*
remoteapplicationname:s:RemoteAppName 2
remoteapplicationprogram:s:C:RemoteAppDirectory2
remoteapplicationcmdline:s:
remoteapplicationicon:s:
"@
    }
)

# Process each RDP profile
foreach ($profile in $rdpProfiles) {
    try {
        $fileName = "$($profile.Name).rdp"
        $iconPath = $profile.IconPath
        $rdpFilePath = Join-Path -Path $remoteAppProfilesFolder -ChildPath $fileName

        # Write the RDP configuration content to the file
        $profile.ConfigurationContent | Out-File -FilePath $rdpFilePath -Force
        Write-Host "RDP profile '$($profile.Name)' created at: $rdpFilePath"

        # Creating shortcut on Desktop
        $desktopPath = [System.Environment]::GetFolderPath('Desktop')
        $shortcutPath = Join-Path -Path $desktopPath -ChildPath ("$($profile.Name).lnk")
        $shortcut = (New-Object -ComObject WScript.Shell).CreateShortcut($shortcutPath)
        $shortcut.TargetPath = $rdpFilePath
        $shortcut.IconLocation = $iconPath
        $shortcut.Save()
        Write-Host "Shortcut for '$($profile.Name)' created at: $shortcutPath"
    } catch {
        Write-Host "Error processing profile '$($profile.Name)': $_"
    }
}