Merge pull request #3007 from PHPOffice/Issue-3005_Extract-CellReferences-in-Range-with-Worksheet-Reference

Adjust `extractAllCellReferencesInRange()` method to allow a worksheet in the reference
This commit is contained in:
Mark Baker 2022-08-15 06:40:50 +02:00 committed by GitHub
commit 4f714cd2a3
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 98 additions and 12 deletions

View File

@ -1060,11 +1060,6 @@ parameters:
count: 1
path: src/PhpSpreadsheet/Calculation/TextData/Text.php
-
message: "#^Elseif branch is unreachable because previous condition is always true\\.$#"
count: 1
path: src/PhpSpreadsheet/Cell/Cell.php
-
message: "#^Method PhpOffice\\\\PhpSpreadsheet\\\\Cell\\\\Cell\\:\\:getFormulaAttributes\\(\\) has no return type specified\\.$#"
count: 1

View File

@ -2,6 +2,7 @@
namespace PhpOffice\PhpSpreadsheet\Cell;
use PhpOffice\PhpSpreadsheet\Calculation\Functions;
use PhpOffice\PhpSpreadsheet\Exception;
use PhpOffice\PhpSpreadsheet\Worksheet\Worksheet;
@ -349,6 +350,19 @@ abstract class Coordinate
*/
public static function extractAllCellReferencesInRange($cellRange): array
{
if (substr_count($cellRange, '!') > 1) {
throw new Exception('3-D Range References are not supported');
}
[$worksheet, $cellRange] = Worksheet::extractSheetTitle($cellRange, true);
$quoted = '';
if ($worksheet > '') {
$quoted = Worksheet::nameRequiresQuotes($worksheet) ? "'" : '';
if (substr($worksheet, 0, 1) === "'" && substr($worksheet, -1, 1) === "'") {
$worksheet = substr($worksheet, 1, -1);
}
$worksheet = str_replace("'", "''", $worksheet);
}
[$ranges, $operators] = self::getCellBlocksFromRangeString($cellRange);
$cells = [];
@ -364,7 +378,12 @@ abstract class Coordinate
$cellList = array_merge(...$cells);
return self::sortCellReferenceArray($cellList);
return array_map(
function ($cellAddress) use ($worksheet, $quoted) {
return ($worksheet !== '') ? "{$quoted}{$worksheet}{$quoted}!{$cellAddress}" : $cellAddress;
},
self::sortCellReferenceArray($cellList)
);
}
private static function processRangeSetOperators(array $operators, array $cells): array

View File

@ -32,14 +32,16 @@ use PhpOffice\PhpSpreadsheet\Style\Style;
class Worksheet implements IComparable
{
// Break types
const BREAK_NONE = 0;
const BREAK_ROW = 1;
const BREAK_COLUMN = 2;
public const BREAK_NONE = 0;
public const BREAK_ROW = 1;
public const BREAK_COLUMN = 2;
// Sheet state
const SHEETSTATE_VISIBLE = 'visible';
const SHEETSTATE_HIDDEN = 'hidden';
const SHEETSTATE_VERYHIDDEN = 'veryHidden';
public const SHEETSTATE_VISIBLE = 'visible';
public const SHEETSTATE_HIDDEN = 'hidden';
public const SHEETSTATE_VERYHIDDEN = 'veryHidden';
protected const SHEET_NAME_REQUIRES_NO_QUOTES = '/^[_\p{L}][_\p{L}\p{N}]*$/mui';
/**
* Maximum 31 characters allowed for sheet title.
@ -3037,7 +3039,11 @@ class Worksheet implements IComparable
* Extract worksheet title from range.
*
* Example: extractSheetTitle("testSheet!A1") ==> 'A1'
* Example: extractSheetTitle("testSheet!A1:C3") ==> 'A1:C3'
* Example: extractSheetTitle("'testSheet 1'!A1", true) ==> ['testSheet 1', 'A1'];
* Example: extractSheetTitle("'testSheet 1'!A1:C3", true) ==> ['testSheet 1', 'A1:C3'];
* Example: extractSheetTitle("A1", true) ==> ['', 'A1'];
* Example: extractSheetTitle("A1:C3", true) ==> ['', 'A1:C3']
*
* @param string $range Range to extract title from
* @param bool $returnRange Return range? (see example)
@ -3436,4 +3442,9 @@ class Worksheet implements IComparable
{
return $this->codeName !== null;
}
public static function nameRequiresQuotes(string $sheetName): bool
{
return preg_match(self::SHEET_NAME_REQUIRES_NO_QUOTES, $sheetName) !== 1;
}
}

View File

@ -0,0 +1,28 @@
<?php
use PhpOffice\PhpSpreadsheet\Cell\Coordinate;
error_reporting(E_ALL);
set_time_limit(0);
date_default_timezone_set('UTC');
// Adjust the path as required to reference the PHPSpreadsheet Bootstrap file
require_once __DIR__ . '/../vendor/autoload.php';
$cellRange1 = Coordinate::extractAllCellReferencesInRange('D3');
var_dump($cellRange1);
$cellRange2 = Coordinate::extractAllCellReferencesInRange('D3:E4');
var_dump($cellRange2);
$cellRange3 = Coordinate::extractAllCellReferencesInRange('Sheet1!D3');
var_dump($cellRange3);
$cellRange4 = Coordinate::extractAllCellReferencesInRange('Sheet1!D3:E4');
var_dump($cellRange4);
$cellRange11 = Coordinate::extractAllCellReferencesInRange('D3:E4 D4:F6');
var_dump($cellRange11);
$cellRange12 = Coordinate::extractAllCellReferencesInRange('D3:E4,D4:F6');
var_dump($cellRange12);
$cellRange5 = Coordinate::extractAllCellReferencesInRange('Sheet1!D3:Sheet2!E4');
var_dump($cellRange5);

View File

@ -130,4 +130,37 @@ return [
],
'Z2:AA3',
],
[
[
'Sheet1!D3',
],
'Sheet1!D3',
],
[
[
'Sheet1!D3',
'Sheet1!E3',
'Sheet1!D4',
'Sheet1!E4',
],
'Sheet1!D3:E4',
],
[
[
"'Sheet 1'!D3",
"'Sheet 1'!E3",
"'Sheet 1'!D4",
"'Sheet 1'!E4",
],
"'Sheet 1'!D3:E4",
],
[
[
"'Mark''s Sheet'!D3",
"'Mark''s Sheet'!E3",
"'Mark''s Sheet'!D4",
"'Mark''s Sheet'!E4",
],
"'Mark's Sheet'!D3:E4",
],
];