From cd030d4aa81582e8bc04d029c0be6e42eff9ea47 Mon Sep 17 00:00:00 2001 From: xuri Date: Mon, 23 Aug 2021 00:15:43 +0800 Subject: Improve compatibility with row element with r="0" attribute --- cell_test.go | 17 +++++++++++++++++ excelize.go | 32 ++++++++++++++++++++++++++++++-- 2 files changed, 47 insertions(+), 2 deletions(-) diff --git a/cell_test.go b/cell_test.go index 91dc4fd..7a08560 100644 --- a/cell_test.go +++ b/cell_test.go @@ -225,6 +225,23 @@ func TestGetCellValue(t *testing.T) { rows, err = f.GetRows("Sheet1") assert.Equal(t, [][]string{{"A3"}, {"A4", "B4"}, nil, nil, nil, nil, {"A7", "B7"}, {"A8", "B8"}}, rows) assert.NoError(t, err) + + f.Sheet.Delete("xl/worksheets/sheet1.xml") + f.Pkg.Store("xl/worksheets/sheet1.xml", []byte(fmt.Sprintf(sheetData, `H6r0A6F4A6B6C6100B3`))) + f.checked = nil + cell, err = f.GetCellValue("Sheet1", "H6") + assert.Equal(t, "H6", cell) + assert.NoError(t, err) + rows, err = f.GetRows("Sheet1") + assert.Equal(t, [][]string{ + {"A6", "B6", "C6"}, + nil, + {"100", "B3"}, + {"", "", "", "", "", "F4"}, + nil, + {"", "", "", "", "", "", "", "H6"}, + }, rows) + assert.NoError(t, err) } func TestGetCellFormula(t *testing.T) { diff --git a/excelize.go b/excelize.go index 6e4e4d9..11ddf92 100644 --- a/excelize.go +++ b/excelize.go @@ -226,7 +226,13 @@ func (f *File) workSheetReader(sheet string) (ws *xlsxWorksheet, err error) { // continuous in a worksheet of XML. func checkSheet(ws *xlsxWorksheet) { var row int - for _, r := range ws.SheetData.Row { + var r0 xlsxRow + for i, r := range ws.SheetData.Row { + if i == 0 && r.R == 0 { + r0 = r + ws.SheetData.Row = ws.SheetData.Row[1:] + continue + } if r.R != 0 && r.R > row { row = r.R continue @@ -254,7 +260,29 @@ func checkSheet(ws *xlsxWorksheet) { for i := 1; i <= row; i++ { sheetData.Row[i-1].R = i } - ws.SheetData = sheetData + checkSheetR0(ws, &sheetData, &r0) +} + +// checkSheetR0 handle the row element with r="0" attribute, cells in this row +// could be disorderly, the cell in this row can be used as the value of +// which cell is empty in the normal rows. +func checkSheetR0(ws *xlsxWorksheet, sheetData *xlsxSheetData, r0 *xlsxRow) { + for _, cell := range r0.C { + if col, row, err := CellNameToCoordinates(cell.R); err == nil { + rows, rowIdx := len(sheetData.Row), row-1 + for r := rows; r < row; r++ { + sheetData.Row = append(sheetData.Row, xlsxRow{R: r + 1}) + } + columns, colIdx := len(sheetData.Row[rowIdx].C), col-1 + for c := columns; c < col; c++ { + sheetData.Row[rowIdx].C = append(sheetData.Row[rowIdx].C, xlsxC{}) + } + if !sheetData.Row[rowIdx].C[colIdx].hasValue() { + sheetData.Row[rowIdx].C[colIdx] = cell + } + } + } + ws.SheetData = *sheetData } // addRels provides a function to add relationships by given XML path, -- cgit v1.2.1