Bugfix for Issue #3013, Named ranges not usable as anchors in OFFSET function
This commit is contained in:
parent
d7da206103
commit
269e9ba14d
|
|
@ -687,7 +687,7 @@ class Functions
|
|||
$worksheet2 = $defined->getWorkSheet();
|
||||
if (!$defined->isFormula() && $worksheet2 !== null) {
|
||||
$coordinate = "'" . $worksheet2->getTitle() . "'!" .
|
||||
(string) preg_replace('/^=/', '', $defined->getValue());
|
||||
(string) preg_replace('/^=/', '', str_replace('$', '', $defined->getValue()));
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -99,6 +99,8 @@ class Offset
|
|||
|
||||
private static function extractWorksheet($cellAddress, Cell $cell): array
|
||||
{
|
||||
$cellAddress = self::assessCellAddress($cellAddress, $cell);
|
||||
|
||||
$sheetName = '';
|
||||
if (strpos($cellAddress, '!') !== false) {
|
||||
[$sheetName, $cellAddress] = Worksheet::extractSheetTitle($cellAddress, true);
|
||||
|
|
@ -112,6 +114,15 @@ class Offset
|
|||
return [$cellAddress, $worksheet];
|
||||
}
|
||||
|
||||
private static function assessCellAddress(string $cellAddress, Cell $cell): string
|
||||
{
|
||||
if (preg_match('/^' . Calculation::CALCULATION_REGEXP_DEFINEDNAME . '$/mui', $cellAddress) !== false) {
|
||||
$cellAddress = Functions::expandDefinedName($cellAddress, $cell);
|
||||
}
|
||||
|
||||
return $cellAddress;
|
||||
}
|
||||
|
||||
private static function adjustEndCellColumnForWidth(string $endCellColumn, $width, int $startCellColumn, $columns)
|
||||
{
|
||||
$endCellColumn = Coordinate::columnIndexFromString($endCellColumn) - 1;
|
||||
|
|
|
|||
|
|
@ -5,6 +5,7 @@ namespace PhpOffice\PhpSpreadsheetTests\Calculation\Functions\LookupRef;
|
|||
use PhpOffice\PhpSpreadsheet\Calculation\Calculation;
|
||||
use PhpOffice\PhpSpreadsheet\Calculation\LookupRef;
|
||||
use PhpOffice\PhpSpreadsheet\Cell\Coordinate;
|
||||
use PhpOffice\PhpSpreadsheet\NamedRange;
|
||||
use PhpOffice\PhpSpreadsheet\Spreadsheet;
|
||||
use PHPUnit\Framework\TestCase;
|
||||
|
||||
|
|
@ -91,6 +92,44 @@ class HLookupTest extends TestCase
|
|||
self::assertSame($expectedResult, $result);
|
||||
}
|
||||
|
||||
/**
|
||||
* @dataProvider providerHLookupNamedRange
|
||||
*/
|
||||
public function testHLookupNamedRange(string $expectedResult, string $cellAddress): void
|
||||
{
|
||||
$lookupData = [
|
||||
['Rating', 1, 2, 3, 4],
|
||||
['Level', 'Poor', 'Average', 'Good', 'Excellent'],
|
||||
];
|
||||
$formData = [
|
||||
['Category', 'Rating', 'Level'],
|
||||
['Service', 2, '=HLOOKUP(C5,Lookup_Table,2,FALSE)'],
|
||||
['Quality', 3, '=HLOOKUP(C6,Lookup_Table,2,FALSE)'],
|
||||
['Value', 4, '=HLOOKUP(C7,Lookup_Table,2,FALSE)'],
|
||||
['Cleanliness', 3, '=HLOOKUP(C8,Lookup_Table,2,FALSE)'],
|
||||
];
|
||||
|
||||
$spreadsheet = new Spreadsheet();
|
||||
$worksheet = $spreadsheet->getActiveSheet();
|
||||
$worksheet->fromArray($lookupData, null, 'F4');
|
||||
$worksheet->fromArray($formData, null, 'B4');
|
||||
|
||||
$spreadsheet->addNamedRange(new NamedRange('Lookup_Table', $worksheet, '=$G$4:$J$5'));
|
||||
|
||||
$result = $worksheet->getCell($cellAddress)->getCalculatedValue();
|
||||
self::assertEquals($expectedResult, $result);
|
||||
}
|
||||
|
||||
public function providerHLookupNamedRange(): array
|
||||
{
|
||||
return [
|
||||
['Average', 'D5'],
|
||||
['Good', 'D6'],
|
||||
['Excellent', 'D7'],
|
||||
['Good', 'D8'],
|
||||
];
|
||||
}
|
||||
|
||||
/**
|
||||
* @dataProvider providerHLookupArray
|
||||
*/
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@
|
|||
namespace PhpOffice\PhpSpreadsheetTests\Calculation\Functions\LookupRef;
|
||||
|
||||
use PhpOffice\PhpSpreadsheet\Calculation\LookupRef;
|
||||
use PhpOffice\PhpSpreadsheet\NamedRange;
|
||||
|
||||
class OffsetTest extends AllSetupTeardown
|
||||
{
|
||||
|
|
@ -46,4 +47,18 @@ class OffsetTest extends AllSetupTeardown
|
|||
$sheet->getCell('A5')->setValue('=OFFSET(C1, 0, 0)');
|
||||
self::assertSame(5, $sheet->getCell('A5')->getCalculatedValue());
|
||||
}
|
||||
|
||||
public function testOffsetNamedRange(): void
|
||||
{
|
||||
$workSheet = $this->getSheet();
|
||||
$workSheet->setCellValue('A1', 1);
|
||||
$workSheet->setCellValue('A2', 2);
|
||||
|
||||
$this->getSpreadsheet()->addNamedRange(new NamedRange('demo', $workSheet, '=$A$1'));
|
||||
|
||||
$workSheet->setCellValue('B1', '=demo');
|
||||
$workSheet->setCellValue('B2', '=OFFSET(demo, 1, 0)');
|
||||
|
||||
self::assertSame(2, $workSheet->getCell('B2')->getCalculatedValue());
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue