Search code examples
windowspowershellms-wordms-office

Change the background color of a Word file via PowerShell


How can I change the background color of a Word file via PowerShell?

$wd = New-Object -COM 'Word.Application'
$wd.Visible = $true   # set to $false for production

Get-ChildItem 'C:\1\*.doc' | % {
    $doc = $wd.Documents.Open($_.FullName)

    # Here's the problem
    $doc.Background.Fill.ForeColor.RGB = RGB(192, 192, 192)

    # Switch doc view to Online Layout view
    $doc.ActiveWindow.View.Type = 6

    $doc.Save($true)
    $doc.Close()
}

$wd.Quit()
[Runtime.InteropServices.Marshal]::ReleaseComObject($wd)
[GC]::Collect()
[GC]::WaitForPendingFinalizers()

I'm getting 2 errors :

* RGB : The term 'RGB' is not recognized as the name of a cmdlet...
* Cannot find an overload for "Save" and the argument count: "1".

Solution

  • So lets address the couple of issues I know about...

    RGB : The term 'RGB' is not recognized as the name of a cmdlet...

    Of course you know why that is not working since PowerShell does not have a RGB cmdlet. However if you look at the input for $doc.Background.Fill.ForeColor.RGB it is looking for an integer. Referring to this related article you can see how we can make the transition.

    $doc.Background.Fill.ForeColor.RGB = [long](192 + (192* 256) + (192 * 65536))
    

    There is a caveat that needs to be addressed. While the above code does not cause an error you are going to notice that the colour is not displayed on the document. That is because backround colour is not displayed by default. You will need to enable it.

    $doc.Background.Fill.Visible = $true
    

    Ok, that one is done now how about....

    Cannot find an overload for "Save" and the argument count: "1".

    We use Get-Member to see exactly why

    PS C:\users\Cameron\Downloads> $doc | gm
    
       TypeName: Microsoft.Office.Interop.Word.DocumentClass
    ...
    RunLetterWizard                          Method                void RunLetterWizard([ref] System.Object LetterContent, [ref] System.Object WizardMode), void _Document.Ru...
    Save                                     Method                void Save(), void _Document.Save()                                                                           
    SaveAs                                   Method                void SaveAs([ref] System.Object FileName, [ref] System.Object FileFormat, [ref] System.Object LockComments...
    ...
    

    It does not take any parameters so we simply need to remove $true. The other entries are there just to show some other methods do take parameters.

    $doc.Save()
    

    .... so .... for the last one

    True : The term 'True' is not recognized as the name of a cmdlet...

    I did not see that error and will assume it was a typo that didnt get carried over into the code of your question.

    Still miss RGB?

    A crude PowerShell function that replicates the functionality with a little data validation

    Function Get-RGB 
    { 
        Param( 
            [Parameter(Mandatory=$false)] 
            [ValidateRange(0,255)] 
            [Int] 
            $Red = 0, 
            [Parameter(Mandatory=$false)] 
            [ValidateRange(0,255)] 
            [Int] 
            $Green = 0,
            [Parameter(Mandatory=$false)] 
            [ValidateRange(0,255)] 
            [Int] 
            $Blue = 0 
        ) 
        Process 
        { 
            [long]($Red + ($Green * 256) + ($Blue * 65536))
        } 
    }
    

    Example

    PS C:\users\Cameron\Downloads> Get-RGB 129 0 54
    3539073