Skip to content

Commit dea57dd

Browse files
committed
Code optimize.
1 parent 70f6328 commit dea57dd

10 files changed

+168
-303
lines changed

Diff for: cell.go

+16-28
Original file line numberDiff line numberDiff line change
@@ -6,20 +6,26 @@ import (
66
"strings"
77
)
88

9-
// GetCellValue provides function to get formatted value from cell by given
10-
// sheet index and axis in XLSX file. If it is possible to apply a format to the
11-
// cell value, it will do so, if not then an error will be returned, along with
12-
// the raw value of the cell.
13-
func (f *File) GetCellValue(sheet, axis string) string {
14-
xlsx := f.workSheetReader(sheet)
15-
axis = strings.ToUpper(axis)
9+
// mergeCellsParser provides function to check merged cells in worksheet by
10+
// given axis.
11+
func (f *File) mergeCellsParser(xlsx *xlsxWorksheet, axis string) {
1612
if xlsx.MergeCells != nil {
1713
for i := 0; i < len(xlsx.MergeCells.Cells); i++ {
1814
if checkCellInArea(axis, xlsx.MergeCells.Cells[i].Ref) {
1915
axis = strings.Split(xlsx.MergeCells.Cells[i].Ref, ":")[0]
2016
}
2117
}
2218
}
19+
}
20+
21+
// GetCellValue provides function to get formatted value from cell by given
22+
// sheet index and axis in XLSX file. If it is possible to apply a format to the
23+
// cell value, it will do so, if not then an error will be returned, along with
24+
// the raw value of the cell.
25+
func (f *File) GetCellValue(sheet, axis string) string {
26+
xlsx := f.workSheetReader(sheet)
27+
axis = strings.ToUpper(axis)
28+
f.mergeCellsParser(xlsx, axis)
2329
row, _ := strconv.Atoi(strings.Map(intOnlyMapF, axis))
2430
xAxis := row - 1
2531
rows := len(xlsx.SheetData.Row)
@@ -78,13 +84,7 @@ func (f *File) formattedValue(s int, v string) string {
7884
func (f *File) GetCellFormula(sheet, axis string) string {
7985
xlsx := f.workSheetReader(sheet)
8086
axis = strings.ToUpper(axis)
81-
if xlsx.MergeCells != nil {
82-
for i := 0; i < len(xlsx.MergeCells.Cells); i++ {
83-
if checkCellInArea(axis, xlsx.MergeCells.Cells[i].Ref) {
84-
axis = strings.Split(xlsx.MergeCells.Cells[i].Ref, ":")[0]
85-
}
86-
}
87-
}
87+
f.mergeCellsParser(xlsx, axis)
8888
row, _ := strconv.Atoi(strings.Map(intOnlyMapF, axis))
8989
xAxis := row - 1
9090
rows := len(xlsx.SheetData.Row)
@@ -118,13 +118,7 @@ func (f *File) GetCellFormula(sheet, axis string) string {
118118
func (f *File) SetCellFormula(sheet, axis, formula string) {
119119
xlsx := f.workSheetReader(sheet)
120120
axis = strings.ToUpper(axis)
121-
if xlsx.MergeCells != nil {
122-
for i := 0; i < len(xlsx.MergeCells.Cells); i++ {
123-
if checkCellInArea(axis, xlsx.MergeCells.Cells[i].Ref) {
124-
axis = strings.Split(xlsx.MergeCells.Cells[i].Ref, ":")[0]
125-
}
126-
}
127-
}
121+
f.mergeCellsParser(xlsx, axis)
128122
col := string(strings.Map(letterOnlyMapF, axis))
129123
row, _ := strconv.Atoi(strings.Map(intOnlyMapF, axis))
130124
xAxis := row - 1
@@ -151,13 +145,7 @@ func (f *File) SetCellFormula(sheet, axis, formula string) {
151145
func (f *File) SetCellHyperLink(sheet, axis, link string) {
152146
xlsx := f.workSheetReader(sheet)
153147
axis = strings.ToUpper(axis)
154-
if xlsx.MergeCells != nil {
155-
for i := 0; i < len(xlsx.MergeCells.Cells); i++ {
156-
if checkCellInArea(axis, xlsx.MergeCells.Cells[i].Ref) {
157-
axis = strings.Split(xlsx.MergeCells.Cells[i].Ref, ":")[0]
158-
}
159-
}
160-
}
148+
f.mergeCellsParser(xlsx, axis)
161149
rID := f.addSheetRelationships(sheet, SourceRelationshipHyperLink, link, "External")
162150
hyperlink := xlsxHyperlink{
163151
Ref: axis,

Diff for: chart.go

+71-98
Original file line numberDiff line numberDiff line change
@@ -187,24 +187,12 @@ func (f *File) AddChart(sheet, cell, format string) {
187187
drawingID := f.countDrawings() + 1
188188
chartID := f.countCharts() + 1
189189
drawingXML := "xl/drawings/drawing" + strconv.Itoa(drawingID) + ".xml"
190-
sheetRelationshipsDrawingXML := "../drawings/drawing" + strconv.Itoa(drawingID) + ".xml"
191-
192-
var drawingRID int
193-
if xlsx.Drawing != nil {
194-
// The worksheet already has a picture or chart relationships, use the relationships drawing ../drawings/drawing%d.xml.
195-
sheetRelationshipsDrawingXML = f.getSheetRelationshipsTargetByID(sheet, xlsx.Drawing.RID)
196-
drawingID, _ = strconv.Atoi(strings.TrimSuffix(strings.TrimPrefix(sheetRelationshipsDrawingXML, "../drawings/drawing"), ".xml"))
197-
drawingXML = strings.Replace(sheetRelationshipsDrawingXML, "..", "xl", -1)
198-
} else {
199-
// Add first picture for given sheet.
200-
rID := f.addSheetRelationships(sheet, SourceRelationshipDrawingML, sheetRelationshipsDrawingXML, "")
201-
f.addSheetDrawing(sheet, rID)
202-
}
203-
drawingRID = f.addDrawingRelationships(drawingID, SourceRelationshipChart, "../charts/chart"+strconv.Itoa(chartID)+".xml")
190+
drawingID, drawingXML = f.prepareDrawing(xlsx, drawingID, sheet, drawingXML)
191+
drawingRID := f.addDrawingRelationships(drawingID, SourceRelationshipChart, "../charts/chart"+strconv.Itoa(chartID)+".xml")
204192
f.addDrawingChart(sheet, drawingXML, cell, 480, 290, drawingRID, &formatSet.Format)
205193
f.addChart(formatSet)
206-
f.addChartContentTypePart(chartID)
207-
f.addDrawingContentTypePart(drawingID)
194+
f.addContentTypePart(chartID, "chart")
195+
f.addContentTypePart(drawingID, "drawings")
208196
}
209197

210198
// countCharts provides function to get chart files count storage in the
@@ -219,19 +207,21 @@ func (f *File) countCharts() int {
219207
return count
220208
}
221209

222-
// addChartContentTypePart provides function to add chart part relationships in
223-
// the file [Content_Types].xml by given chart index.
224-
func (f *File) addChartContentTypePart(index int) {
225-
content := f.contentTypesReader()
226-
for _, v := range content.Overrides {
227-
if v.PartName == "/xl/charts/chart"+strconv.Itoa(index)+".xml" {
228-
return
229-
}
210+
// prepareDrawing provides function to prepare drawing ID and XML by given
211+
// drawingID, worksheet index and default drawingXML.
212+
func (f *File) prepareDrawing(xlsx *xlsxWorksheet, drawingID int, sheet, drawingXML string) (int, string) {
213+
sheetRelationshipsDrawingXML := "../drawings/drawing" + strconv.Itoa(drawingID) + ".xml"
214+
if xlsx.Drawing != nil {
215+
// The worksheet already has a picture or chart relationships, use the relationships drawing ../drawings/drawing%d.xml.
216+
sheetRelationshipsDrawingXML = f.getSheetRelationshipsTargetByID(sheet, xlsx.Drawing.RID)
217+
drawingID, _ = strconv.Atoi(strings.TrimSuffix(strings.TrimPrefix(sheetRelationshipsDrawingXML, "../drawings/drawing"), ".xml"))
218+
drawingXML = strings.Replace(sheetRelationshipsDrawingXML, "..", "xl", -1)
219+
} else {
220+
// Add first picture for given sheet.
221+
rID := f.addSheetRelationships(sheet, SourceRelationshipDrawingML, sheetRelationshipsDrawingXML, "")
222+
f.addSheetDrawing(sheet, rID)
230223
}
231-
content.Overrides = append(content.Overrides, xlsxOverride{
232-
PartName: "/xl/charts/chart" + strconv.Itoa(index) + ".xml",
233-
ContentType: "application/vnd.openxmlformats-officedocument.drawingml.chart+xml",
234-
})
224+
return drawingID, drawingXML
235225
}
236226

237227
// addChart provides function to create chart as xl/charts/chart%d.xml by given
@@ -364,7 +354,7 @@ func (f *File) addChart(formatSet *formatChart) {
364354
}
365355
plotAreaFunc := map[string]func(*formatChart) *cPlotArea{
366356
Bar: f.drawBarChart,
367-
Bar3D: f.drawBar3DChart,
357+
Bar3D: f.drawBarChart,
368358
Doughnut: f.drawDoughnutChart,
369359
Line: f.drawLineChart,
370360
Pie3D: f.drawPie3DChart,
@@ -379,56 +369,39 @@ func (f *File) addChart(formatSet *formatChart) {
379369
f.saveFileList(media, string(chart))
380370
}
381371

382-
// drawBarChart provides function to draw the c:plotArea element for bar chart
383-
// by given format sets.
372+
// drawBarChart provides function to draw the c:plotArea element for bar and
373+
// bar3D chart by given format sets.
384374
func (f *File) drawBarChart(formatSet *formatChart) *cPlotArea {
385-
return &cPlotArea{
386-
BarChart: &cCharts{
387-
BarDir: &attrValString{
388-
Val: "col",
389-
},
390-
Grouping: &attrValString{
391-
Val: "clustered",
392-
},
393-
VaryColors: &attrValBool{
394-
Val: true,
395-
},
396-
Ser: f.drawChartSeries(formatSet),
397-
DLbls: f.drawChartDLbls(formatSet),
398-
AxID: []*attrValInt{
399-
{Val: 754001152},
400-
{Val: 753999904},
401-
},
375+
c := cCharts{
376+
BarDir: &attrValString{
377+
Val: "col",
378+
},
379+
Grouping: &attrValString{
380+
Val: "clustered",
381+
},
382+
VaryColors: &attrValBool{
383+
Val: true,
384+
},
385+
Ser: f.drawChartSeries(formatSet),
386+
DLbls: f.drawChartDLbls(formatSet),
387+
AxID: []*attrValInt{
388+
{Val: 754001152},
389+
{Val: 753999904},
402390
},
403-
CatAx: f.drawPlotAreaCatAx(),
404-
ValAx: f.drawPlotAreaValAx(),
405391
}
406-
}
407-
408-
// drawBar3DChart provides function to draw the c:plotArea element for 3D bar
409-
// chart by given format sets.
410-
func (f *File) drawBar3DChart(formatSet *formatChart) *cPlotArea {
411-
return &cPlotArea{
412-
Bar3DChart: &cCharts{
413-
BarDir: &attrValString{
414-
Val: "col",
415-
},
416-
Grouping: &attrValString{
417-
Val: "clustered",
418-
},
419-
VaryColors: &attrValBool{
420-
Val: true,
421-
},
422-
Ser: f.drawChartSeries(formatSet),
423-
DLbls: f.drawChartDLbls(formatSet),
424-
AxID: []*attrValInt{
425-
{Val: 754001152},
426-
{Val: 753999904},
427-
},
392+
charts := map[string]*cPlotArea{
393+
"bar": &cPlotArea{
394+
BarChart: &c,
395+
CatAx: f.drawPlotAreaCatAx(),
396+
ValAx: f.drawPlotAreaValAx(),
397+
},
398+
"bar3D": &cPlotArea{
399+
Bar3DChart: &c,
400+
CatAx: f.drawPlotAreaCatAx(),
401+
ValAx: f.drawPlotAreaValAx(),
428402
},
429-
CatAx: f.drawPlotAreaCatAx(),
430-
ValAx: f.drawPlotAreaValAx(),
431403
}
404+
return charts[formatSet.Type]
432405
}
433406

434407
// drawDoughnutChart provides function to draw the c:plotArea element for
@@ -711,15 +684,7 @@ func (f *File) drawChartDLbls(formatSet *formatChart) *cDLbls {
711684
// drawChartSeriesDLbls provides function to draw the c:dLbls element by given
712685
// format sets.
713686
func (f *File) drawChartSeriesDLbls(formatSet *formatChart) *cDLbls {
714-
dLbls := &cDLbls{
715-
ShowLegendKey: &attrValBool{Val: formatSet.Legend.ShowLegendKey},
716-
ShowVal: &attrValBool{Val: formatSet.Plotarea.ShowVal},
717-
ShowCatName: &attrValBool{Val: formatSet.Plotarea.ShowCatName},
718-
ShowSerName: &attrValBool{Val: formatSet.Plotarea.ShowSerName},
719-
ShowBubbleSize: &attrValBool{Val: formatSet.Plotarea.ShowBubbleSize},
720-
ShowPercent: &attrValBool{Val: formatSet.Plotarea.ShowPercent},
721-
ShowLeaderLines: &attrValBool{Val: formatSet.Plotarea.ShowLeaderLines},
722-
}
687+
dLbls := f.drawChartDLbls(formatSet)
723688
chartSeriesDLbls := map[string]*cDLbls{Bar: dLbls, Bar3D: dLbls, Doughnut: dLbls, Line: dLbls, Pie: dLbls, Pie3D: dLbls, Radar: dLbls, Scatter: nil}
724689
return chartSeriesDLbls[formatSet.Type]
725690
}
@@ -837,21 +802,11 @@ func (f *File) drawPlotAreaTxPr() *cTxPr {
837802
}
838803
}
839804

840-
// addDrawingChart provides function to add chart graphic frame by given sheet,
841-
// drawingXML, cell, width, height, relationship index and format sets.
842-
func (f *File) addDrawingChart(sheet, drawingXML, cell string, width, height, rID int, formatSet *formatPicture) {
843-
cell = strings.ToUpper(cell)
844-
fromCol := string(strings.Map(letterOnlyMapF, cell))
845-
fromRow, _ := strconv.Atoi(strings.Map(intOnlyMapF, cell))
846-
row := fromRow - 1
847-
col := titleToNumber(fromCol)
848-
width = int(float64(width) * formatSet.XScale)
849-
height = int(float64(height) * formatSet.YScale)
850-
colStart, rowStart, _, _, colEnd, rowEnd, x2, y2 := f.positionObjectPixels(sheet, col, row, formatSet.OffsetX, formatSet.OffsetY, width, height)
851-
content := xlsxWsDr{}
852-
content.A = NameSpaceDrawingML
853-
content.Xdr = NameSpaceDrawingMLSpreadSheet
854-
cNvPrID := 1
805+
// drawingParser provides function to parse drawingXML. In order to solve the
806+
// problem that the label structure is changed after serialization and
807+
// deserialization, two different structures: decodeWsDr and encodeWsDr are
808+
// defined.
809+
func (f *File) drawingParser(drawingXML string, cNvPrID int, content *xlsxWsDr) {
855810
_, ok := f.XLSX[drawingXML]
856811
if ok { // Append Model
857812
decodeWsDr := decodeWsDr{}
@@ -870,6 +825,24 @@ func (f *File) addDrawingChart(sheet, drawingXML, cell string, width, height, rI
870825
})
871826
}
872827
}
828+
}
829+
830+
// addDrawingChart provides function to add chart graphic frame by given sheet,
831+
// drawingXML, cell, width, height, relationship index and format sets.
832+
func (f *File) addDrawingChart(sheet, drawingXML, cell string, width, height, rID int, formatSet *formatPicture) {
833+
cell = strings.ToUpper(cell)
834+
fromCol := string(strings.Map(letterOnlyMapF, cell))
835+
fromRow, _ := strconv.Atoi(strings.Map(intOnlyMapF, cell))
836+
row := fromRow - 1
837+
col := titleToNumber(fromCol)
838+
width = int(float64(width) * formatSet.XScale)
839+
height = int(float64(height) * formatSet.YScale)
840+
colStart, rowStart, _, _, colEnd, rowEnd, x2, y2 := f.positionObjectPixels(sheet, col, row, formatSet.OffsetX, formatSet.OffsetY, width, height)
841+
content := xlsxWsDr{}
842+
content.A = NameSpaceDrawingML
843+
content.Xdr = NameSpaceDrawingMLSpreadSheet
844+
cNvPrID := 1
845+
f.drawingParser(drawingXML, cNvPrID, &content)
873846
twoCellAnchor := xdrCellAnchor{}
874847
twoCellAnchor.EditAs = "oneCell"
875848
from := xlsxFrom{}

Diff for: comment.go

+1-1
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@ func (f *File) AddComment(sheet, cell, format string) {
4747
commentsXML := "xl/comments" + strconv.Itoa(commentID) + ".xml"
4848
f.addComment(commentsXML, cell, formatSet)
4949
f.addDrawingVML(commentID, drawingVML, cell)
50-
f.addCommentsContentTypePart(commentID)
50+
f.addContentTypePart(commentID, "comments")
5151
}
5252

5353
// addDrawingVML provides function to create comment as

Diff for: excelize.go

+4-22
Original file line numberDiff line numberDiff line change
@@ -123,13 +123,7 @@ func (f *File) workSheetReader(sheet string) *xlsxWorksheet {
123123
func (f *File) SetCellInt(sheet, axis string, value int) {
124124
xlsx := f.workSheetReader(sheet)
125125
axis = strings.ToUpper(axis)
126-
if xlsx.MergeCells != nil {
127-
for i := 0; i < len(xlsx.MergeCells.Cells); i++ {
128-
if checkCellInArea(axis, xlsx.MergeCells.Cells[i].Ref) {
129-
axis = strings.Split(xlsx.MergeCells.Cells[i].Ref, ":")[0]
130-
}
131-
}
132-
}
126+
f.mergeCellsParser(xlsx, axis)
133127
col := string(strings.Map(letterOnlyMapF, axis))
134128
row, _ := strconv.Atoi(strings.Map(intOnlyMapF, axis))
135129
xAxis := row - 1
@@ -150,13 +144,7 @@ func (f *File) SetCellInt(sheet, axis string, value int) {
150144
func (f *File) SetCellStr(sheet, axis, value string) {
151145
xlsx := f.workSheetReader(sheet)
152146
axis = strings.ToUpper(axis)
153-
if xlsx.MergeCells != nil {
154-
for i := 0; i < len(xlsx.MergeCells.Cells); i++ {
155-
if checkCellInArea(axis, xlsx.MergeCells.Cells[i].Ref) {
156-
axis = strings.Split(xlsx.MergeCells.Cells[i].Ref, ":")[0]
157-
}
158-
}
159-
}
147+
f.mergeCellsParser(xlsx, axis)
160148
if len(value) > 32767 {
161149
value = value[0:32767]
162150
}
@@ -189,13 +177,7 @@ func (f *File) SetCellStr(sheet, axis, value string) {
189177
func (f *File) SetCellDefault(sheet, axis, value string) {
190178
xlsx := f.workSheetReader(sheet)
191179
axis = strings.ToUpper(axis)
192-
if xlsx.MergeCells != nil {
193-
for i := 0; i < len(xlsx.MergeCells.Cells); i++ {
194-
if checkCellInArea(axis, xlsx.MergeCells.Cells[i].Ref) {
195-
axis = strings.Split(xlsx.MergeCells.Cells[i].Ref, ":")[0]
196-
}
197-
}
198-
}
180+
f.mergeCellsParser(xlsx, axis)
199181
col := string(strings.Map(letterOnlyMapF, axis))
200182
row, _ := strconv.Atoi(strings.Map(intOnlyMapF, axis))
201183
xAxis := row - 1
@@ -272,7 +254,7 @@ func completeRow(xlsx *xlsxWorksheet, row, cell int) {
272254
// continuous in a worksheet of XML.
273255
func checkSheet(xlsx *xlsxWorksheet) {
274256
row := len(xlsx.SheetData.Row)
275-
if row > 1 {
257+
if row >= 1 {
276258
lastRow := xlsx.SheetData.Row[row-1].R
277259
if lastRow >= row {
278260
row = lastRow

0 commit comments

Comments
 (0)