@@ -1113,12 +1113,9 @@ public function getHighestRowAndColumn()
11131113 * @param null|array<int>|CellAddress|string $cellAddress Coordinate of the cell as a string, eg: 'C5';
11141114 * or as an array of [$columnIndex, $row] (e.g. [3, 5]), or a CellAddress object.
11151115 */
1116- protected function validateCellAddress ($ cellAddress, bool $ allowNull = false ): ? string
1116+ protected function validateCellAddress ($ cellAddress ): string
11171117 {
1118- if (is_string ($ cellAddress ) || ($ cellAddress === null && $ allowNull === true )) {
1119- if ($ cellAddress === null ) {
1120- return null ;
1121- }
1118+ if (is_string ($ cellAddress )) {
11221119 [$ worksheet , $ address ] = self ::extractSheetTitle ($ cellAddress , true );
11231120// if (!empty($worksheet) && $worksheet !== $this->getTitle()) {
11241121// throw new Exception('Reference is not for this worksheet');
@@ -1134,16 +1131,38 @@ protected function validateCellAddress($cellAddress, bool $allowNull = false): ?
11341131 return (string ) $ cellAddress ;
11351132 }
11361133
1134+ private function tryDefinedName (string $ coordinate ): string
1135+ {
1136+ // Uppercase coordinate
1137+ $ coordinate = strtoupper ($ coordinate );
1138+ // Eliminate leading equal sign
1139+ $ coordinate = self ::pregReplace ('/^=/ ' , '' , $ coordinate );
1140+ $ defined = $ this ->parent ->getDefinedName ($ coordinate , $ this );
1141+ if ($ defined !== null ) {
1142+ if ($ defined ->getWorksheet () === $ this && !$ defined ->isFormula ()) {
1143+ $ coordinate = self ::pregReplace ('/^=/ ' , '' , $ defined ->getValue ());
1144+ }
1145+ }
1146+
1147+ return $ coordinate ;
1148+ }
1149+
11371150 /**
1138- * Validate a cell range.
1151+ * Validate a cell address or cell range.
11391152 *
1140- * @param AddressRange|array<int>|CellAddress|string $cellRange Coordinate of the cells as a string, eg: 'C5:F12';
1153+ * @param AddressRange|array<int>|CellAddress|int| string $cellRange Coordinate of the cells as a string, eg: 'C5:F12';
11411154 * or as an array of [$fromColumnIndex, $fromRow, $toColumnIndex, $toRow] (e.g. [3, 5, 6, 12]),
11421155 * or as a CellAddress or AddressRange object.
11431156 */
11441157 protected function validateCellOrCellRange ($ cellRange ): string
11451158 {
1146- if (is_object ($ cellRange ) && $ cellRange instanceof CellAddress) {
1159+ if (is_string ($ cellRange ) || is_numeric ($ cellRange )) {
1160+ $ cellRange = (string ) $ cellRange ;
1161+ // Convert a single column reference like 'A' to 'A:A'
1162+ $ cellRange = self ::pregReplace ('/^([A-Z]+)$/ ' , '${1}:${1} ' , $ cellRange );
1163+ // Convert a single row reference like '1' to '1:1'
1164+ $ cellRange = self ::pregReplace ('/^(\d+)$/ ' , '${1}:${1} ' , $ cellRange );
1165+ } elseif (is_object ($ cellRange ) && $ cellRange instanceof CellAddress) {
11471166 $ cellRange = new CellRange ($ cellRange , $ cellRange );
11481167 }
11491168
@@ -1162,9 +1181,9 @@ protected function validateCellRange($cellRange): string
11621181 if (is_string ($ cellRange )) {
11631182 [$ worksheet , $ addressRange ] = self ::extractSheetTitle ($ cellRange , true );
11641183
1165- // Convert 'A:C' to 'A1:C1048576'
1184+ // Convert Column ranges like 'A:C' to 'A1:C1048576'
11661185 $ addressRange = self ::pregReplace ('/^([A-Z]+):([A-Z]+)$/ ' , '${1}1:${2}1048576 ' , $ addressRange );
1167- // Convert '1:3' to 'A1:XFD3'
1186+ // Convert Row ranges like '1:3' to 'A1:XFD3'
11681187 $ addressRange = self ::pregReplace ('/^( \\d+):( \\d+)$/ ' , 'A${1}:XFD${2} ' , $ addressRange );
11691188
11701189 return empty ($ worksheet ) ? strtoupper ($ addressRange ) : $ worksheet . '! ' . strtoupper ($ addressRange );
@@ -1189,8 +1208,7 @@ protected function validateCellRange($cellRange): string
11891208 */
11901209 public function setCellValue ($ coordinate , $ value )
11911210 {
1192- /** @var string $cellAddress */
1193- $ cellAddress = $ this ->validateCellAddress ($ coordinate );
1211+ $ cellAddress = Functions::trimSheetFromCellReference ($ this ->validateCellAddress ($ coordinate ));
11941212 $ this ->getCell ($ cellAddress )->setValue ($ value );
11951213
11961214 return $ this ;
@@ -1211,7 +1229,7 @@ public function setCellValue($coordinate, $value)
12111229 */
12121230 public function setCellValueByColumnAndRow ($ columnIndex , $ row , $ value )
12131231 {
1214- $ this ->getCell ([ $ columnIndex, $ row] )->setValue ($ value );
1232+ $ this ->getCell (Coordinate:: stringFromColumnIndex ( $ columnIndex) . $ row )->setValue ($ value );
12151233
12161234 return $ this ;
12171235 }
@@ -1228,8 +1246,7 @@ public function setCellValueByColumnAndRow($columnIndex, $row, $value)
12281246 */
12291247 public function setCellValueExplicit ($ coordinate , $ value , $ dataType )
12301248 {
1231- /** @var string $cellAddress */
1232- $ cellAddress = $ this ->validateCellAddress ($ coordinate );
1249+ $ cellAddress = Functions::trimSheetFromCellReference ($ this ->validateCellAddress ($ coordinate ));
12331250 $ this ->getCell ($ cellAddress )->setValueExplicit ($ value , $ dataType );
12341251
12351252 return $ this ;
@@ -1251,7 +1268,7 @@ public function setCellValueExplicit($coordinate, $value, $dataType)
12511268 */
12521269 public function setCellValueExplicitByColumnAndRow ($ columnIndex , $ row , $ value , $ dataType )
12531270 {
1254- $ this ->getCell ([ $ columnIndex, $ row] )->setValueExplicit ($ value , $ dataType );
1271+ $ this ->getCell (Coordinate:: stringFromColumnIndex ( $ columnIndex) . $ row )->setValueExplicit ($ value , $ dataType );
12551272
12561273 return $ this ;
12571274 }
@@ -1266,8 +1283,7 @@ public function setCellValueExplicitByColumnAndRow($columnIndex, $row, $value, $
12661283 */
12671284 public function getCell ($ coordinate ): Cell
12681285 {
1269- /** @var string $cellAddress */
1270- $ cellAddress = $ this ->validateCellAddress ($ coordinate );
1286+ $ cellAddress = Functions::trimSheetFromCellReference ($ this ->validateCellAddress ($ coordinate ));
12711287
12721288 // Shortcut for increased performance for the vast majority of simple cases
12731289 if ($ this ->cellCollection ->has ($ cellAddress )) {
@@ -1368,7 +1384,7 @@ private function getCellOrNull($coordinate): ?Cell
13681384 */
13691385 public function getCellByColumnAndRow ($ columnIndex , $ row ): Cell
13701386 {
1371- return $ this ->getCell ([ $ columnIndex, $ row] );
1387+ return $ this ->getCell (Coordinate:: stringFromColumnIndex ( $ columnIndex) . $ row );
13721388 }
13731389
13741390 /**
@@ -1418,7 +1434,6 @@ public function createNewCell($coordinate)
14181434 */
14191435 public function cellExists ($ coordinate ): bool
14201436 {
1421- /** @var string $cellAddress */
14221437 $ cellAddress = $ this ->validateCellAddress ($ coordinate );
14231438 /** @var Worksheet $sheet */
14241439 [$ sheet , $ finalCoordinate ] = $ this ->getWorksheetAndCoordinate ($ cellAddress );
@@ -1438,7 +1453,7 @@ public function cellExists($coordinate): bool
14381453 */
14391454 public function cellExistsByColumnAndRow ($ columnIndex , $ row ): bool
14401455 {
1441- return $ this ->cellExists ([ $ columnIndex, $ row] );
1456+ return $ this ->cellExists (Coordinate:: stringFromColumnIndex ( $ columnIndex) . $ row );
14421457 }
14431458
14441459 /**
@@ -1504,14 +1519,14 @@ public function getStyles()
15041519 /**
15051520 * Get style for cell.
15061521 *
1507- * @param AddressRange|array<int>|CellAddress|string $cellCoordinate
1522+ * @param AddressRange|array<int>|CellAddress|int| string $cellCoordinate
15081523 * A simple string containing a cell address like 'A1' or a cell range like 'A1:E10'
15091524 * or passing in an array of [$fromColumnIndex, $fromRow, $toColumnIndex, $toRow] (e.g. [3, 5, 6, 8]),
15101525 * or a CellAddress or AddressRange object.
15111526 */
15121527 public function getStyle ($ cellCoordinate ): Style
15131528 {
1514- $ cellCoordinate = $ this ->validateCellRange ($ cellCoordinate );
1529+ $ cellCoordinate = $ this ->validateCellOrCellRange ($ cellCoordinate );
15151530
15161531 // set this sheet as active
15171532 $ this ->parent ->setActiveSheetIndex ($ this ->parent ->getIndex ($ this ));
@@ -1749,7 +1764,7 @@ public function duplicateConditionalStyle(array $styles, $range = '')
17491764 */
17501765 public function setBreak ($ coordinate , $ break )
17511766 {
1752- $ cellAddress = Functions::trimSheetFromCellReference ($ this ->validateCellAddress ($ coordinate ) ?? '' );
1767+ $ cellAddress = Functions::trimSheetFromCellReference ($ this ->validateCellAddress ($ coordinate ));
17531768
17541769 if ($ break === self ::BREAK_NONE ) {
17551770 if (isset ($ this ->breaks [$ cellAddress ])) {
@@ -1777,7 +1792,7 @@ public function setBreak($coordinate, $break)
17771792 */
17781793 public function setBreakByColumnAndRow ($ columnIndex , $ row , $ break )
17791794 {
1780- return $ this ->setBreak ([ $ columnIndex, $ row] , $ break );
1795+ return $ this ->setBreak (Coordinate:: stringFromColumnIndex ( $ columnIndex) . $ row , $ break );
17811796 }
17821797
17831798 /**
@@ -1978,7 +1993,7 @@ public function setMergeCells(array $mergeCells)
19781993 /**
19791994 * Set protection on a cell or cell range.
19801995 *
1981- * @param AddressRange|array<int>|CellAddress|string $range A simple string containing a Cell range like 'A1:E10'
1996+ * @param AddressRange|array<int>|CellAddress|int| string $range A simple string containing a Cell range like 'A1:E10'
19821997 * or passing in an array of [$fromColumnIndex, $fromRow, $toColumnIndex, $toRow] (e.g. [3, 5, 6, 8]),
19831998 * or a CellAddress or AddressRange object.
19841999 * @param string $password Password to unlock the protection
@@ -1988,7 +2003,7 @@ public function setMergeCells(array $mergeCells)
19882003 */
19892004 public function protectCells ($ range , $ password , $ alreadyHashed = false )
19902005 {
1991- $ range = Functions::trimSheetFromCellReference ($ this ->validateCellRange ($ range ));
2006+ $ range = Functions::trimSheetFromCellReference ($ this ->validateCellOrCellRange ($ range ));
19922007
19932008 if (!$ alreadyHashed ) {
19942009 $ password = Shared \PasswordHasher::hashPassword ($ password );
@@ -2028,15 +2043,15 @@ public function protectCellsByColumnAndRow($columnIndex1, $row1, $columnIndex2,
20282043 /**
20292044 * Remove protection on a cell or cell range.
20302045 *
2031- * @param AddressRange|array<int>|CellAddress|string $range A simple string containing a Cell range like 'A1:E10'
2046+ * @param AddressRange|array<int>|CellAddress|int| string $range A simple string containing a Cell range like 'A1:E10'
20322047 * or passing in an array of [$fromColumnIndex, $fromRow, $toColumnIndex, $toRow] (e.g. [3, 5, 6, 8]),
20332048 * or a CellAddress or AddressRange object.
20342049 *
20352050 * @return $this
20362051 */
20372052 public function unprotectCells ($ range )
20382053 {
2039- $ range = Functions::trimSheetFromCellReference ($ this ->validateCellRange ($ range ));
2054+ $ range = Functions::trimSheetFromCellReference ($ this ->validateCellOrCellRange ($ range ));
20402055
20412056 if (isset ($ this ->protectedCells [$ range ])) {
20422057 unset($ this ->protectedCells [$ range ]);
@@ -2180,11 +2195,15 @@ public function getFreezePane()
21802195 */
21812196 public function freezePane ($ coordinate , $ topLeftCell = null )
21822197 {
2183- $ cellAddress = $ this ->validateCellAddress ($ coordinate , true );
2184- if (is_string ($ cellAddress ) && Coordinate::coordinateIsRange ($ cellAddress )) {
2198+ $ cellAddress = ($ coordinate !== null )
2199+ ? Functions::trimSheetFromCellReference ($ this ->validateCellAddress ($ coordinate ))
2200+ : null ;
2201+ if ($ cellAddress !== null && Coordinate::coordinateIsRange ($ cellAddress )) {
21852202 throw new Exception ('Freeze pane can not be set on a range of cells. ' );
21862203 }
2187- $ topLeftCell = $ this ->validateCellAddress ($ topLeftCell , true );
2204+ $ topLeftCell = ($ topLeftCell !== null )
2205+ ? Functions::trimSheetFromCellReference ($ this ->validateCellAddress ($ topLeftCell ))
2206+ : null ;
21882207
21892208 if ($ cellAddress !== null && $ topLeftCell === null ) {
21902209 $ coordinate = Coordinate::coordinateFromString ($ cellAddress );
@@ -2218,7 +2237,7 @@ public function setTopLeftCell(string $topLeftCell): self
22182237 */
22192238 public function freezePaneByColumnAndRow ($ columnIndex , $ row )
22202239 {
2221- return $ this ->freezePane ([ $ columnIndex, $ row] );
2240+ return $ this ->freezePane (Coordinate:: stringFromColumnIndex ( $ columnIndex) . $ row );
22222241 }
22232242
22242243 /**
@@ -2587,8 +2606,7 @@ public function setComments(array $comments)
25872606 */
25882607 public function getComment ($ cellCoordinate )
25892608 {
2590- /** @var string $cellAddress */
2591- $ cellAddress = $ this ->validateCellAddress ($ cellCoordinate );
2609+ $ cellAddress = Functions::trimSheetFromCellReference ($ this ->validateCellAddress ($ cellCoordinate ));
25922610
25932611 if (Coordinate::coordinateIsRange ($ cellAddress )) {
25942612 throw new Exception ('Cell coordinate string can not be a range of cells. ' );
@@ -2624,7 +2642,7 @@ public function getComment($cellCoordinate)
26242642 */
26252643 public function getCommentByColumnAndRow ($ columnIndex , $ row )
26262644 {
2627- return $ this ->getComment ([ $ columnIndex, $ row] );
2645+ return $ this ->getComment (Coordinate:: stringFromColumnIndex ( $ columnIndex) . $ row );
26282646 }
26292647
26302648 /**
@@ -2675,48 +2693,21 @@ public static function pregReplace(string $pattern, string $replacement, string
26752693 return self ::ensureString (preg_replace ($ pattern , $ replacement , $ subject ));
26762694 }
26772695
2678- private function tryDefinedName (string $ coordinate ): string
2679- {
2680- // Uppercase coordinate
2681- $ coordinate = strtoupper ($ coordinate );
2682- // Eliminate leading equal sign
2683- $ coordinate = self ::pregReplace ('/^=/ ' , '' , $ coordinate );
2684- $ defined = $ this ->parent ->getDefinedName ($ coordinate , $ this );
2685- if ($ defined !== null ) {
2686- if ($ defined ->getWorksheet () === $ this && !$ defined ->isFormula ()) {
2687- $ coordinate = self ::pregReplace ('/^=/ ' , '' , $ defined ->getValue ());
2688- }
2689- }
2690-
2691- return $ coordinate ;
2692- }
2693-
26942696 /**
26952697 * Select a range of cells.
26962698 *
2697- * @param string $coordinate Cell range, examples: 'A1', 'B2:G5', 'A:C', '3:6'
2699+ * @param AddressRange|array<int>|CellAddress|int|string $coordinate A simple string containing a Cell range like 'A1:E10'
2700+ * or passing in an array of [$fromColumnIndex, $fromRow, $toColumnIndex, $toRow] (e.g. [3, 5, 6, 8]),
2701+ * or a CellAddress or AddressRange object.
26982702 *
26992703 * @return $this
27002704 */
27012705 public function setSelectedCells ($ coordinate )
27022706 {
2703- $ originalCoordinate = $ coordinate ;
2704- $ coordinate = $ this ->tryDefinedName ($ coordinate );
2705-
2706- // Convert 'A' to 'A:A'
2707- $ coordinate = self ::pregReplace ('/^([A-Z]+)$/ ' , '${1}:${1} ' , $ coordinate );
2708-
2709- // Convert '1' to '1:1'
2710- $ coordinate = self ::pregReplace ('/^(\d+)$/ ' , '${1}:${1} ' , $ coordinate );
2711-
2712- // Convert 'A:C' to 'A1:C1048576'
2713- $ coordinate = self ::pregReplace ('/^([A-Z]+):([A-Z]+)$/ ' , '${1}1:${2}1048576 ' , $ coordinate );
2714-
2715- // Convert '1:3' to 'A1:XFD3'
2716- $ coordinate = self ::pregReplace ('/^(\d+):(\d+)$/ ' , 'A${1}:XFD${2} ' , $ coordinate );
2717- if (preg_match ('/^ \\$?[A-Z]{1,3} \\$?\d{1,7}(: \\$?[A-Z]{1,3} \\$?\d{1,7})?$/ ' , $ coordinate ) !== 1 ) {
2718- throw new Exception ("Invalid setSelectedCells $ originalCoordinate $ coordinate " );
2707+ if (is_string ($ coordinate )) {
2708+ $ coordinate = $ this ->tryDefinedName ($ coordinate );
27192709 }
2710+ $ coordinate = $ this ->validateCellOrCellRange ($ coordinate );
27202711
27212712 if (Coordinate::coordinateIsRange ($ coordinate )) {
27222713 [$ first ] = Coordinate::splitRange ($ coordinate );
0 commit comments