Vendor/phpspreadsheet/phpoffice/phpspreadsheet/src/PhpSpreadsheet/Style/Style.php
public function applyFromArray(array $pStyles, $pAdvanced = true)
    {
        if ($this->isSupervisor) {
            $pRange = $this->getSelectedCells();

            // Uppercase coordinate
            $pRange = strtoupper($pRange);

            // Is it a cell range or a single cell?
            if (strpos($pRange, ':') === false) {
                $rangeA = $pRange;
                $rangeB = $pRange;
            } else {
                list($rangeA, $rangeB) = explode(':', $pRange);
            }

            // Calculate range outer borders
            $rangeStart = Coordinate::coordinateFromString($rangeA);
            $rangeEnd = Coordinate::coordinateFromString($rangeB);

            // Translate column into index
            $rangeStart[0] = Coordinate::columnIndexFromString($rangeStart[0]);
            $rangeEnd[0] = Coordinate::columnIndexFromString($rangeEnd[0]);

            // Make sure we can loop upwards on rows and columns
            if ($rangeStart[0] > $rangeEnd[0] && $rangeStart[1] > $rangeEnd[1]) {
                $tmp = $rangeStart;
                $rangeStart = $rangeEnd;
                $rangeEnd = $tmp;
            }

            // ADVANCED MODE:
            if ($pAdvanced && isset($pStyles['borders'])) {
                // 'allBorders' is a shorthand property for 'outline' and 'inside' and
                //        it applies to components that have not been set explicitly
                if (isset($pStyles['borders']['allBorders'])) {
                    foreach (['outline', 'inside'] as $component) {
                        if (!isset($pStyles['borders'][$component])) {
                            $pStyles['borders'][$component] = $pStyles['borders']['allBorders'];
                        }
                    }
                    unset($pStyles['borders']['allBorders']); // not needed any more
                }
                // 'outline' is a shorthand property for 'top', 'right', 'bottom', 'left'
                //        it applies to components that have not been set explicitly
                if (isset($pStyles['borders']['outline'])) {
                    foreach (['top', 'right', 'bottom', 'left'] as $component) {
                        if (!isset($pStyles['borders'][$component])) {
                            $pStyles['borders'][$component] = $pStyles['borders']['outline'];
                        }
                    }
                    unset($pStyles['borders']['outline']); // not needed any more
                }
                // 'inside' is a shorthand property for 'vertical' and 'horizontal'
                //        it applies to components that have not been set explicitly
                if (isset($pStyles['borders']['inside'])) {
                    foreach (['vertical', 'horizontal'] as $component) {
                        if (!isset($pStyles['borders'][$component])) {
                            $pStyles['borders'][$component] = $pStyles['borders']['inside'];
                        }
                    }
                    unset($pStyles['borders']['inside']); // not needed any more
                }
                // width and height characteristics of selection, 1, 2, or 3 (for 3 or more)
                $xMax = min($rangeEnd[0] - $rangeStart[0] + 1, 3);
                $yMax = min($rangeEnd[1] - $rangeStart[1] + 1, 3);

                // loop through up to 3 x 3 = 9 regions
                for ($x = 1; $x <= $xMax; ++$x) {
                    // start column index for region
                    $colStart = ($x == 3) ?
                        Coordinate::stringFromColumnIndex($rangeEnd[0])
                            : Coordinate::stringFromColumnIndex($rangeStart[0] + $x - 1);
                    // end column index for region
                    $colEnd = ($x == 1) ?
                        Coordinate::stringFromColumnIndex($rangeStart[0])
                            : Coordinate::stringFromColumnIndex($rangeEnd[0] - $xMax + $x);

                    for ($y = 1; $y <= $yMax; ++$y) {
                        // which edges are touching the region
                        $edges = [];
                        if ($x == 1) {
                            // are we at left edge
                            $edges[] = 'left';
                        }
                        if ($x == $xMax) {
                            // are we at right edge
                            $edges[] = 'right';
                        }
                        if ($y == 1) {
                            // are we at top edge?
                            $edges[] = 'top';
                        }
                        if ($y == $yMax) {
                            // are we at bottom edge?
                            $edges[] = 'bottom';
                        }

                        // start row index for region
                        $rowStart = ($y == 3) ?
                            $rangeEnd[1] : $rangeStart[1] + $y - 1;

                        // end row index for region
                        $rowEnd = ($y == 1) ?
                            $rangeStart[1] : $rangeEnd[1] - $yMax + $y;

                        // build range for region
                        $range = $colStart . $rowStart . ':' . $colEnd . $rowEnd;

                        // retrieve relevant style array for region
                        $regionStyles = $pStyles;
                        unset($regionStyles['borders']['inside']);

                        // what are the inner edges of the region when looking at the selection
                        $innerEdges = array_diff(['top', 'right', 'bottom', 'left'], $edges);

                        // inner edges that are not touching the region should take the 'inside' border properties if they have been set
                        foreach ($innerEdges as $innerEdge) {
                            switch ($innerEdge) {
                                case 'top':
                                case 'bottom':
                                    // should pick up 'horizontal' border property if set
                                    if (isset($pStyles['borders']['horizontal'])) {
                                        $regionStyles['borders'][$innerEdge] = $pStyles['borders']['horizontal'];
                                    } else {
                                        unset($regionStyles['borders'][$innerEdge]);
                                    }

                                    break;
                                case 'left':
                                case 'right':
                                    // should pick up 'vertical' border property if set
                                    if (isset($pStyles['borders']['vertical'])) {
                                        $regionStyles['borders'][$innerEdge] = $pStyles['borders']['vertical'];
                                    } else {
                                        unset($regionStyles['borders'][$innerEdge]);
                                    }

                                    break;
                            }
                        }

                        // apply region style to region by calling applyFromArray() in simple mode
                        $this->getActiveSheet()->getStyle($range)->applyFromArray($regionStyles, false);
                    }
                }

                return $this;
            }

            // SIMPLE MODE:
            // Selection type, inspect
            if (preg_match('/^[A-Z]+1:[A-Z]+1048576$/', $pRange)) {
                $selectionType = 'COLUMN';
            } elseif (preg_match('/^A\d+:XFD\d+$/', $pRange)) {
                $selectionType = 'ROW';
            } else {
                $selectionType = 'CELL';
            }

            // First loop through columns, rows, or cells to find out which styles are affected by this operation
            switch ($selectionType) {
                case 'COLUMN':
                    $oldXfIndexes = [];
                    for ($col = $rangeStart[0]; $col <= $rangeEnd[0]; ++$col) {
                        $oldXfIndexes[$this->getActiveSheet()->getColumnDimensionByColumn($col)->getXfIndex()] = true;
                    }

                    break;
                case 'ROW':
                    $oldXfIndexes = [];
                    for ($row = $rangeStart[1]; $row <= $rangeEnd[1]; ++$row) {
                        if ($this->getActiveSheet()->getRowDimension($row)->getXfIndex() == null) {
                            $oldXfIndexes[0] = true; // row without explicit style should be formatted based on default style
                        } else {
                            $oldXfIndexes[$this->getActiveSheet()->getRowDimension($row)->getXfIndex()] = true;
                        }
                    }

                    break;
                case 'CELL':
                    $oldXfIndexes = [];
                    for ($col = $rangeStart[0]; $col <= $rangeEnd[0]; ++$col) {
                        for ($row = $rangeStart[1]; $row <= $rangeEnd[1]; ++$row) {
                            $oldXfIndexes[$this->getActiveSheet()->getCellByColumnAndRow($col, $row)->getXfIndex()] = true;
                        }
                    }

                    break;
            }

            // clone each of the affected styles, apply the style array, and add the new styles to the workbook
            $workbook = $this->getActiveSheet()->getParent();
            foreach ($oldXfIndexes as $oldXfIndex => $dummy) {
                $style = $workbook->getCellXfByIndex($oldXfIndex);
                $newStyle = clone $style;
                $newStyle->applyFromArray($pStyles);

                if ($existingStyle = $workbook->getCellXfByHashCode($newStyle->getHashCode())) {
                    // there is already such cell Xf in our collection
                    $newXfIndexes[$oldXfIndex] = $existingStyle->getIndex();
                } else {
                    // we don't have such a cell Xf, need to add
                    $workbook->addCellXf($newStyle);
                    $newXfIndexes[$oldXfIndex] = $newStyle->getIndex();
                }
            }

            // Loop through columns, rows, or cells again and update the XF index
            switch ($selectionType) {
                case 'COLUMN':
                    for ($col = $rangeStart[0]; $col <= $rangeEnd[0]; ++$col) {
                        $columnDimension = $this->getActiveSheet()->getColumnDimensionByColumn($col);
                        $oldXfIndex = $columnDimension->getXfIndex();
                        $columnDimension->setXfIndex($newXfIndexes[$oldXfIndex]);
                    }

                    break;
                case 'ROW':
                    for ($row = $rangeStart[1]; $row <= $rangeEnd[1]; ++$row) {
                        $rowDimension = $this->getActiveSheet()->getRowDimension($row);
                        $oldXfIndex = $rowDimension->getXfIndex() === null ?
                            0 : $rowDimension->getXfIndex(); // row without explicit style should be formatted based on default style
                        $rowDimension->setXfIndex($newXfIndexes[$oldXfIndex]);
                    }

                    break;
                case 'CELL':
                    for ($col = $rangeStart[0]; $col <= $rangeEnd[0]; ++$col) {
                        for ($row = $rangeStart[1]; $row <= $rangeEnd[1]; ++$row) {
                            $cell = $this->getActiveSheet()->getCellByColumnAndRow($col, $row);
                            $oldXfIndex = $cell->getXfIndex();
                            $cell->setXfIndex($newXfIndexes[$oldXfIndex]);
                        }
                    }

                    break;
            }
        } else {
            // not a supervisor, just apply the style array directly on style object
            if (isset($pStyles['fill'])) {
                $this->getFill()->applyFromArray($pStyles['fill']);
            }
            if (isset($pStyles['font'])) {
                $this->getFont()->applyFromArray($pStyles['font']);
            }
            if (isset($pStyles['borders'])) {
                $this->getBorders()->applyFromArray($pStyles['borders']);
            }
            if (isset($pStyles['alignment'])) {
                $this->getAlignment()->applyFromArray($pStyles['alignment']);
            }
            if (isset($pStyles['numberFormat'])) {
                $this->getNumberFormat()->applyFromArray($pStyles['numberFormat']);
            }
            if (isset($pStyles['protection'])) {
                $this->getProtection()->applyFromArray($pStyles['protection']);
            }
            if (isset($pStyles['quotePrefix'])) {
                $this->quotePrefix = $pStyles['quotePrefix'];
            }
        }

        return $this;
    }
public function applyFromArray(array $pStyles, $pAdvanced = true)
    {
        if ($this->isSupervisor) {
            $pRange = $this->getSelectedCells();

            // Uppercase coordinate
            $pRange = strtoupper($pRange);

            // Is it a cell range or a single cell?
            if (strpos($pRange, ':') === false) {
                $rangeA = $pRange;
                $rangeB = $pRange;
            } else {
                list($rangeA, $rangeB) = explode(':', $pRange);
            }

            // Calculate range outer borders
            $rangeStart = Coordinate::coordinateFromString($rangeA);
            $rangeEnd = Coordinate::coordinateFromString($rangeB);

            // Translate column into index
            $rangeStart[0] = Coordinate::columnIndexFromString($rangeStart[0]);
            $rangeEnd[0] = Coordinate::columnIndexFromString($rangeEnd[0]);

            // Make sure we can loop upwards on rows and columns
            if ($rangeStart[0] > $rangeEnd[0] && $rangeStart[1] > $rangeEnd[1]) {
                $tmp = $rangeStart;
                $rangeStart = $rangeEnd;
                $rangeEnd = $tmp;
            }

            // ADVANCED MODE:
            if ($pAdvanced && isset($pStyles['borders'])) {
                // 'allBorders' is a shorthand property for 'outline' and 'inside' and
                //        it applies to components that have not been set explicitly
                if (isset($pStyles['borders']['allBorders'])) {
                    foreach (['outline', 'inside'] as $component) {
                        if (!isset($pStyles['borders'][$component])) {
                            $pStyles['borders'][$component] = $pStyles['borders']['allBorders'];
                        }
                    }
                    unset($pStyles['borders']['allBorders']); // not needed any more
                }
                // 'outline' is a shorthand property for 'top', 'right', 'bottom', 'left'
                //        it applies to components that have not been set explicitly
                if (isset($pStyles['borders']['outline'])) {
                    foreach (['top', 'right', 'bottom', 'left'] as $component) {
                        if (!isset($pStyles['borders'][$component])) {
                            $pStyles['borders'][$component] = $pStyles['borders']['outline'];
                        }
                    }
                    unset($pStyles['borders']['outline']); // not needed any more
                }
                // 'inside' is a shorthand property for 'vertical' and 'horizontal'
                //        it applies to components that have not been set explicitly
                if (isset($pStyles['borders']['inside'])) {
                    foreach (['vertical', 'horizontal'] as $component) {
                        if (!isset($pStyles['borders'][$component])) {
                            $pStyles['borders'][$component] = $pStyles['borders']['inside'];
                        }
                    }
                    unset($pStyles['borders']['inside']); // not needed any more
                }
                // width and height characteristics of selection, 1, 2, or 3 (for 3 or more)
                $xMax = min($rangeEnd[0] - $rangeStart[0] + 1, 3);
                $yMax = min($rangeEnd[1] - $rangeStart[1] + 1, 3);

                // loop through up to 3 x 3 = 9 regions
                for ($x = 1; $x <= $xMax; ++$x) {
                    // start column index for region
                    $colStart = ($x == 3) ?
                        Coordinate::stringFromColumnIndex($rangeEnd[0])
                            : Coordinate::stringFromColumnIndex($rangeStart[0] + $x - 1);
                    // end column index for region
                    $colEnd = ($x == 1) ?
                        Coordinate::stringFromColumnIndex($rangeStart[0])
                            : Coordinate::stringFromColumnIndex($rangeEnd[0] - $xMax + $x);

                    for ($y = 1; $y <= $yMax; ++$y) {
                        // which edges are touching the region
                        $edges = [];
                        if ($x == 1) {
                            // are we at left edge
                            $edges[] = 'left';
                        }
                        if ($x == $xMax) {
                            // are we at right edge
                            $edges[] = 'right';
                        }
                        if ($y == 1) {
                            // are we at top edge?
                            $edges[] = 'top';
                        }
                        if ($y == $yMax) {
                            // are we at bottom edge?
                            $edges[] = 'bottom';
                        }

                        // start row index for region
                        $rowStart = ($y == 3) ?
                            $rangeEnd[1] : $rangeStart[1] + $y - 1;

                        // end row index for region
                        $rowEnd = ($y == 1) ?
                            $rangeStart[1] : $rangeEnd[1] - $yMax + $y;

                        // build range for region
                        $range = $colStart . $rowStart . ':' . $colEnd . $rowEnd;

                        // retrieve relevant style array for region
                        $regionStyles = $pStyles;
                        unset($regionStyles['borders']['inside']);

                        // what are the inner edges of the region when looking at the selection
                        $innerEdges = array_diff(['top', 'right', 'bottom', 'left'], $edges);

                        // inner edges that are not touching the region should take the 'inside' border properties if they have been set
                        foreach ($innerEdges as $innerEdge) {
                            switch ($innerEdge) {
                                case 'top':
                                case 'bottom':
                                    // should pick up 'horizontal' border property if set
                                    if (isset($pStyles['borders']['horizontal'])) {
                                        $regionStyles['borders'][$innerEdge] = $pStyles['borders']['horizontal'];
                                    } else {
                                        unset($regionStyles['borders'][$innerEdge]);
                                    }

                                    break;
                                case 'left':
                                case 'right':
                                    // should pick up 'vertical' border property if set
                                    if (isset($pStyles['borders']['vertical'])) {
                                        $regionStyles['borders'][$innerEdge] = $pStyles['borders']['vertical'];
                                    } else {
                                        unset($regionStyles['borders'][$innerEdge]);
                                    }

                                    break;
                            }
                        }

                        // apply region style to region by calling applyFromArray() in simple mode
                        $this->getActiveSheet()->getStyle($range)->applyFromArray($regionStyles, false);
                    }
                }

                return $this;
            }

            // SIMPLE MODE:
            // Selection type, inspect
            if (preg_match('/^[A-Z]+1:[A-Z]+1048576$/', $pRange)) {
                $selectionType = 'COLUMN';
            } elseif (preg_match('/^A\d+:XFD\d+$/', $pRange)) {
                $selectionType = 'ROW';
            } else {
                $selectionType = 'CELL';
            }

            // First loop through columns, rows, or cells to find out which styles are affected by this operation
            switch ($selectionType) {
                case 'COLUMN':
                    $oldXfIndexes = [];
                    for ($col = $rangeStart[0]; $col <= $rangeEnd[0]; ++$col) {
                        $oldXfIndexes[$this->getActiveSheet()->getColumnDimensionByColumn($col)->getXfIndex()] = true;
                    }

                    break;
                case 'ROW':
                    $oldXfIndexes = [];
                    for ($row = $rangeStart[1]; $row <= $rangeEnd[1]; ++$row) {
                        if ($this->getActiveSheet()->getRowDimension($row)->getXfIndex() == null) {
                            $oldXfIndexes[0] = true; // row without explicit style should be formatted based on default style
                        } else {
                            $oldXfIndexes[$this->getActiveSheet()->getRowDimension($row)->getXfIndex()] = true;
                        }
                    }

                    break;
                case 'CELL':
                    $oldXfIndexes = [];
                    for ($col = $rangeStart[0]; $col <= $rangeEnd[0]; ++$col) {
                        for ($row = $rangeStart[1]; $row <= $rangeEnd[1]; ++$row) {
                            $oldXfIndexes[$this->getActiveSheet()->getCellByColumnAndRow($col, $row)->getXfIndex()] = true;
                        }
                    }

                    break;
            }

            // clone each of the affected styles, apply the style array, and add the new styles to the workbook
            $workbook = $this->getActiveSheet()->getParent();
            foreach ($oldXfIndexes as $oldXfIndex => $dummy) {
                $style = $workbook->getCellXfByIndex($oldXfIndex);
                $newStyle = clone $style;
                $newStyle->applyFromArray($pStyles);

                if ($existingStyle = $workbook->getCellXfByHashCode($newStyle->getHashCode())) {
                    // there is already such cell Xf in our collection
                    $newXfIndexes[$oldXfIndex] = $existingStyle->getIndex();
                } else {
                    // we don't have such a cell Xf, need to add
                    $workbook->addCellXf($newStyle);
                    $newXfIndexes[$oldXfIndex] = $newStyle->getIndex();
                }
            }

            // Loop through columns, rows, or cells again and update the XF index
            switch ($selectionType) {
                case 'COLUMN':
                    for ($col = $rangeStart[0]; $col <= $rangeEnd[0]; ++$col) {
                        $columnDimension = $this->getActiveSheet()->getColumnDimensionByColumn($col);
                        $oldXfIndex = $columnDimension->getXfIndex();
                        $columnDimension->setXfIndex($newXfIndexes[$oldXfIndex]);
                    }

                    break;
                case 'ROW':
                    for ($row = $rangeStart[1]; $row <= $rangeEnd[1]; ++$row) {
                        $rowDimension = $this->getActiveSheet()->getRowDimension($row);
                        $oldXfIndex = $rowDimension->getXfIndex() === null ?
                            0 : $rowDimension->getXfIndex(); // row without explicit style should be formatted based on default style
                        $rowDimension->setXfIndex($newXfIndexes[$oldXfIndex]);
                    }

                    break;
                case 'CELL':
                    for ($col = $rangeStart[0]; $col <= $rangeEnd[0]; ++$col) {
                        for ($row = $rangeStart[1]; $row <= $rangeEnd[1]; ++$row) {
                            $cell = $this->getActiveSheet()->getCellByColumnAndRow($col, $row);
                            $oldXfIndex = $cell->getXfIndex();
                            $cell->setXfIndex($newXfIndexes[$oldXfIndex]);
                        }
                    }

                    break;
            }
        } else {
            // not a supervisor, just apply the style array directly on style object
            if (isset($pStyles['fill'])) {
                $this->getFill()->applyFromArray($pStyles['fill']);
            }
            if (isset($pStyles['font'])) {
                $this->getFont()->applyFromArray($pStyles['font']);
            }
            if (isset($pStyles['borders'])) {
                $this->getBorders()->applyFromArray($pStyles['borders']);
            }
            if (isset($pStyles['alignment'])) {
                $this->getAlignment()->applyFromArray($pStyles['alignment']);
            }
            if (isset($pStyles['numberFormat'])) {
                $this->getNumberFormat()->applyFromArray($pStyles['numberFormat']);
            }
            if (isset($pStyles['protection'])) {
                $this->getProtection()->applyFromArray($pStyles['protection']);
            }
            if (isset($pStyles['quotePrefix'])) {
                $this->quotePrefix = $pStyles['quotePrefix'];
            }
        }

        return $this;
    }
Apply styles from array.

<code>
$spreadsheet->getActiveSheet()->getStyle('B2')->applyFromArray(
[
'font' => [
'name' => 'Arial',
'bold' => true,
'italic' => false,
'underline' => Font::UNDERLINE_DOUBLE,
'strikethrough' => false,
'color' => [
'rgb' => '808080'
]
],
'borders' => [
'bottom' => [
'borderStyle' => Border::BORDER_DASHDOT,
'color' => [
'rgb' => '808080'
]
],
'top' => [
'borderStyle' => Border::BORDER_DASHDOT,
'color' => [
'rgb' => '808080'
]
]
],
'quotePrefix'    => true
]
);
</code>

@param array $pStyles Array containing style information
@param bool $pAdvanced advanced mode for setting borders

@return Style