Powershell : Highlight excel cell Interior using condition - excel

I want to highlight an excel cell interior using powershell , am able to change color of font , but not entire cell color
So this is how my excel sheet is , it checks whether the cell has "Matching" and changes color according to that
$excel = New-Object -ComObject Excel.Application
$excel.Visible = $false
$excel.DisplayAlerts = $False
$workbook = $excel.Workbooks.Open("C:\Users\test4.xls")
$sheet = $workbook.ActiveSheet
$xlCellTypeLastCell = 11
$used = $sheet.usedRange
$lastCell = $used.SpecialCells($xlCellTypeLastCell)
$row = $lastCell.row # goes to the last used row in the worksheet
$column = $lastCell.Column;
$i = 0
for ($J = 2; $J -le $column; $j++) {
$sheet.Cells.Item($i,$j).Interior.ColorIndex = 48
$sheet.Cells.Item($i,$j).Font.Bold=$True
}
for ($i = 2; $i -le $row; $i++) {
for($j = 5 ; $j -le $column ; $j++){
if (($sheet.cells.Item($i,$j).Value()) -like "*Matching") {
$sheet.Cells.Item($i,$j).Font.ColorIndex = 10
$sheet.Cells.Item($i,$j).Font.Bold = $true
}
if(($sheet.cells.Item($i,$j).Value()) -like "*Not Matching"){
$sheet.Cells.Item($i,$j).Font.ColorIndex = 3
$sheet.Cells.Item($i,$j).Font.Bold = $true
}
}
}
$workbook.SaveAs("C:\Users\output.xls")
$workbook.Close()
this is code , Only problem is when i give
$sheet.Cells.Item($i,$j).Interior.ColorIndex = 48
It's giving me an exception
Exception from HRESULT: 0x800A03EC
I want my table to look like this ,

Extending from my comments.
PowerShell Excel and Conditional Formatting
# Quick Find the Top 10 Months
$xl = Open-ExcelPackage -Path $xlfile
Add-ConditionalFormatting -Worksheet $xl.StoresTop10Sales -Address $xl.StoresTop10Sales.dimension.address -RuleType Top -ForegroundColor white -BackgroundColor green -ConditionValue 10
Close-ExcelPackage $xl -Show
# Databars
Add-ConditionalFormatting -Worksheet $xl.StoresSalesDataBar -Address $xl.StoresSalesDataBar.dimension.address -DataBarColor Red
# Color Scales
Add-ConditionalFormatting -Worksheet $xl.StoresSalesTwoColorScale -Address $xl.StoresSalesDataBar.dimension.address -RuleType TwoColorScale
Use this module: ImportExcel 5.4.4
AddConditionalFormatting.ps1

So if I understand correctly, you are saying "I want to do with Powershell what Excel can do automatically using condional formatting", do you mean by that:
You are not aware of conditional formatting, or:
Conditional formatting means modifying something in your Excel file, which you can't do, hence the Powershell. Like this your question becomes "How to configure conditional formatting via Powershell?".
Which one is it?

Related

Find a value in Excel via PowerShell

I have a script that find a row with a specific background color. I want to add a condition that if the cell has a color 14 and contains the word cab and I will copy it to a different folder. All the greens (color 14)will copy to other folder. currently all the green cells (14) copied to the same folder
Maybe I need more if condition ? or one more object that holds all the cell that has color 14 and with the string inside? (patch is the name of the column)
I need an object with all the 14 colors and one object with all the 14 colors and has a name like cab
$ExcelFile = "C:\Temp\SharedFolder\Side VIP - Bulk Tool.xlsx"
$searchValue = ''
$excel = New-Object -ComObject Excel.Application
$Excel.Visible = $false
$Excel.DisplayAlerts = $False # Disable comfirmation prompts
$workbook = $excel.Workbooks.Open($ExcelFile)
$worksheet = $workbook.Worksheets.Item("VIP List")
# get the number of rows in the sheet
$rowMax = $worksheet.UsedRange.Rows.Count
# loop through the rows to test if the value in column 1 equals whatever is in $searchValue
# and capture the results in variable $result
$result = for ($row = 1; $row -le $rowMax; $row++) {
$val = $worksheet.Cells.Item($row, 27).Interior.ColorIndex
if ($val -eq 14 -and $val -ne "cab") {
[PsCustomObject]#{Patch = $worksheet.Cells.Item($row, 1).Value2}
}
}
write-host
-join("Number of patches:" + $result.count)
write-host
#$val = $worksheet.Cells.Item($row, 1).Interior.ColorIndex; if ($val -eq 3) { ... }
foreach ($res in $result)
{$vars = foreach ($res in $result) { "\\google.com\global\Patch Managment\$($res.patch)\*" }}
$des = "C:\Temp\SharedFolder\SideVIP"
foreach ($var in $vars)
{
write-host $var
Copy-Item -Path $var -include "*.VIP","*.ZIP"-Destination $des -Force
}

Powershell using ImportExcel to delete rows

I am trying to delete rows of data from an Excel file using the ImportExcel module.
I can open the file, find the the data I wish to delete and the DeleteRow command works on a hardcoded value however does not appear to work on a variable...any ideas?
# Gets ImportExcel PowerShell Module
if (-not(Get-Module -ListAvailable -Name ImportExcel)) {
Find-module -Name ImportExcel | Install-Module -Force
}
# Open Excel File
$excel = open-excelpackage 'C:\temp\input.xlsx'
#Set Worksheet
$ws = $excel.Workbook.Worksheets["Sheet1"]
#Get Row Count
$rowcount = $ws.Dimension.Rows
#Delete row if Cell in Column 15 = Yes
for ($i = 2; $i -lt $rowcount; $i++) {
$cell = $ws.Cells[$i, 15]
if ($cell.value -eq "Yes") {
$ws.DeleteRow($i)
}
}
#Save File
Close-ExcelPackage $excel -SaveAs 'C:\Temp\Output.xlsx'
You should reverse the loop and go from bottom to top row. As you have it, by deleting a row, the index of the ones below that is changed and your for ($i = 2; $i -lt $rowcount; $i++) {..} will skip over.
You can also do this without the ImportExcel module if you have Excel installed:
$file = 'C:\Temp\input.xlsx'
$excel = New-Object -ComObject Excel.Application
$excel.Visible = $false
# open the Excel file
$workbook = $excel.Workbooks.Open($file)
$sheet = $workbook.Worksheets.Item(1)
# get the number of rows in the sheet
$rowMax = $sheet.UsedRange.Rows.Count
# loop through the rows to test if the value in column 15 is "Yes"
# do the loop BACKWARDS, otherwise the indices will change on every deletion.
for ($row = $rowMax; $row -ge 2; $row--) {
$cell = $sheet.Cells[$row, 15].Value2
if ($cell -eq 'Yes') {
$null = $sheet.Rows($row).EntireRow.Delete()
}
}
# save and exit
$workbook.SaveAs("C:\Temp\Output.xlsx")
$excel.Quit()
# clean up the COM objects used
$null = [System.Runtime.Interopservices.Marshal]::ReleaseComObject($sheet)
$null = [System.Runtime.Interopservices.Marshal]::ReleaseComObject($workbook)
$null = [System.Runtime.Interopservices.Marshal]::ReleaseComObject($excel)
[System.GC]::Collect()
[System.GC]::WaitForPendingFinalizers()

Powershell find and replace in Excel

I have about 20 Excel reports.. All headers are the same and the formats of the cells are all the same. In column H on a Tab named Response the header is "Sensor Version" the cells are filled with numbers as such 006.002.001454 I am trying to get powershell to find and replace 00 so that there are no preceding 0's in the numbers. Is there a way to do this, and more importantly is there a way to only apply this to column H since other area's of the workbook potentially can have 00 in a cell.
This code should work:
$excelFile = "excel File.xlsx"
$objExcel = New-Object -ComObject Excel.Application
$WorkBook = $objExcel.Workbooks.Open($excelFile)
$worksheet = $WorkBook.sheets.item("Response")
$rowCount = $worksheet.usedrange.rows.count
$ColumnNumber = $worksheet.cells.find("Sensor Version").column
$newValues = $worksheet.usedrange.columns.item($ColumnNumber).value2 |% { $_ -split "00(.)" -join ""}
for ($i = 2; $i -le $rowCount; $i++) {
$workSheet.cells($i,$ColumnNumber).value = $worksheet.cells($i,$ColumnNumber).text -split "00(.)" -join ""
}
$workBook.close()
This will open each file in Read-Only mode, so you will have a prompt for each save attempt. You can loop through each Excel file by encompassing the entire code block in a ForEach loop and set each file path value to $excelFile.

Excel add Row Grouping using powershell

I have below csv file, I want to import into excel and add the row grouping for the child items using powershell. I was able open the file and format the cell. Not sure how to add row grouping.
Data
name,,
one,,
,value1,value2
,value3 ,value4
two,,
,value4,sevalue4
,value5,sevalue5
,value6,sevalue6
,value7,sevalue7
three,,
,value8,sevalue8
,value9,sevalue9
,value10,sevalue10
,value11,sevalue11
I want to convert like this in excel.
Here is the code I have it to open it in excel.
$a = New-Object -comobject Excel.Application
$a.visible = $True
$b = $a.Workbooks.Open("C:\shared\c1.csv")
$c = $b.Worksheets.Item(1)
$d = $c.Cells(1,1)
$d.Interior.ColorIndex = 19
$d.Font.ColorIndex = 11
$d.Font.Bold = $True
$b.Save("C:\shared\c1.xlsx")
How do I add row grouping for this data?
Thanks
SR
Logic Applied:
Group all the consecutive rows for which the value in column A is blank
In the following code, I have opened a CSV file, made the required grouping as per the data shared by you and saved it. While saving it, because of the row grouping, I was not able to save it in csv format. So, I had to change the format to a normal workbook. But, it works.
Code
$objExl = New-Object -ComObject Excel.Application
$objExl.visible = $true
$objExl.DisplayAlerts = $false
$strPath = "C:\Users\gurmansingh\Documents\a.csv" #Enter the path of csv
$objBook = $objExl.Workbooks.open($strPath)
$objSheet = $objBook.Worksheets.item(1)
$intRowCount = $objSheet.usedRange.Rows.Count
for($i=1; $i -le $intRowCount; $i++)
{
if($objSheet.Cells.Item($i,1).text -like "")
{
$startRow = $i
for($j=$i+1; $j -le $intRowCount; $j++)
{
if($objSheet.cells.Item($j,1).text -ne "" -or $j -eq $intRowCount)
{
$endRow = $j-1
if($j -eq $intRowCount)
{
$endRow = $j
}
break
}
}
$str = "A"+$startRow+":A"+$endRow
$objSheet.Range($str).Rows.Group()
$i=$j
}
}
$objBook.SaveAs("C:\Users\gurmansingh\Documents\b",51) #saving in a different format.
$objBook.Close()
$objExl.Quit()
Before:
a.csv
Output after running the code:
b.xlsx
Also, check out how easy it is to do using my Excel PowerShell module.
Install-Module ImportExcel
https://github.com/dfinke/ImportExcel/issues/556#issuecomment-469897886

Powershell script to match condition of excel cell values

I am novice programmer of powershell, I am trying to do excel search and change of format and font option. Here is the snippet were I am trying to search for the word "PASSED" and change the color to green and bold, currently the code does exits out without changing as expected what is wrong in this which I could not figure out, need help in this regards.
$excel = New-Object -ComObject Excel.Application
$excel.Visible = $false
$excel.DisplayAlerts = $False
$workbook = $excel.Workbooks.Open("C:\test.xlsx")
$sheet = $workbook.ActiveSheet
$xlCellTypeLastCell = 11
$used = $sheet.usedRange
$lastCell = $used.SpecialCells($xlCellTypeLastCell)
$row = $lastCell.row # goes to the last used row in the worksheet
for ($i = 1; $i -lt $row.length; $i++) {
If ($sheet.cells.Item(1,2).Value() = "PASSED") {
$sheet.Cells.Item(1,$i+1).Font.ColorIndex = 10
$sheet.Cells.Item(1,$i+1).Font.Bold = $true
}
}
$workbook.SaveAs("C:\output.xlsx")
$workbook.Close()
Input(test.xlsx) file has the following
Module | test | Status
ABC a PASSED
Its quiet a huge file with different status of each unit test.
$row is a string containing the last row number, comparing to it's Length property in the for loop will land you in trouble since it'll give you the length of the string itself.
Change it to:
for ($i = 1; $i -lt $row; $i++) {
In the if statement inside the loop, there's another problem: =
In order to compare two values for equality, use the -eq operator instead of = (= is only for assignment):
if ($sheet.cells.Item($i,2).Value() -eq "PASSED") {
$sheet.Cells.Item(1,$i+1).Font.ColorIndex = 10
$sheet.Cells.Item(1,$i+1).Font.Bold = $true
}
Lastly, Excel cell references are not zero-based, so Item(1,2) will refer to the cell that in your example has the value "test" (notice how it takes a row as the first parameter, and a column as the second). Change it to Item(2,3) to test against the correct cell, and transpose the cell coordinates inside the if block as well.
You may want to update the for loop to reflect this as well:
for ($i = 2; $i -le $row; $i++) {
if ($sheet.cells.Item($i,3).Value() = "PASSED") {
$sheet.Cells.Item($i,3).Font.ColorIndex = 10
$sheet.Cells.Item($i,3).Font.Bold = $true
}
}

Resources