diff options
-rw-r--r-- | cell.go | 8 | ||||
-rw-r--r-- | cell_test.go | 22 | ||||
-rw-r--r-- | chart.go | 9 | ||||
-rw-r--r-- | chart_test.go | 2 | ||||
-rw-r--r-- | drawing.go | 10 | ||||
-rw-r--r-- | styles.go | 29 | ||||
-rw-r--r-- | xmlChart.go | 4 | ||||
-rw-r--r-- | xmlStyles.go | 18 |
8 files changed, 67 insertions, 35 deletions
@@ -823,6 +823,10 @@ func getCellRichText(si *xlsxSI) (runs []RichTextRun) { font.Strike = v.RPr.Strike != nil if v.RPr.Color != nil { font.Color = strings.TrimPrefix(v.RPr.Color.RGB, "FF") + if v.RPr.Color.Theme != nil { + font.ColorTheme = v.RPr.Color.Theme + } + font.ColorTint = v.RPr.Color.Tint } run.Font = &font } @@ -879,9 +883,7 @@ func newRpr(fnt *Font) *xlsxRPr { if fnt.Size > 0 { rpr.Sz = &attrValFloat{Val: &fnt.Size} } - if fnt.Color != "" { - rpr.Color = &xlsxColor{RGB: getPaletteColor(fnt.Color)} - } + rpr.Color = newFontColor(fnt) return &rpr } diff --git a/cell_test.go b/cell_test.go index 7598058..511078e 100644 --- a/cell_test.go +++ b/cell_test.go @@ -518,7 +518,7 @@ func TestSetCellFormula(t *testing.T) { } func TestGetCellRichText(t *testing.T) { - f := NewFile() + f, theme := NewFile(), 1 runsSource := []RichTextRun{ { @@ -527,13 +527,15 @@ func TestGetCellRichText(t *testing.T) { { Text: "b", Font: &Font{ - Underline: "single", - Color: "ff0000", - Bold: true, - Italic: true, - Family: "Times New Roman", - Size: 100, - Strike: true, + Underline: "single", + Color: "ff0000", + ColorTheme: &theme, + ColorTint: 0.5, + Bold: true, + Italic: true, + Family: "Times New Roman", + Size: 100, + Strike: true, }, }, } @@ -580,6 +582,10 @@ func TestGetCellRichText(t *testing.T) { // Test set cell rich text with illegal cell reference _, err = f.GetCellRichText("Sheet1", "A") assert.EqualError(t, err, newCellNameToCoordinatesError("A", newInvalidCellNameError("A")).Error()) + // Test set rich text color theme without tint + assert.NoError(t, f.SetCellRichText("Sheet1", "A1", []RichTextRun{{Font: &Font{ColorTheme: &theme}}})) + // Test set rich text color tint without theme + assert.NoError(t, f.SetCellRichText("Sheet1", "A1", []RichTextRun{{Font: &Font{ColorTint: 0.5}}})) } func TestSetCellRichText(t *testing.T) { @@ -702,7 +702,7 @@ func parseChartOptions(opts string) (*chartOptions, error) { // // title // -// name: Set the name (title) for the chart. The name is displayed above the chart. The name can also be a formula such as Sheet1!$A$1 or a list with a sheetname. The name property is optional. The default is to have no chart title. +// name: Set the name (title) for the chart. The name is displayed above the chart. The name can also be a formula such as Sheet1!$A$1 or a list with a sheet name. The name property is optional. The default is to have no chart title. // // Specifies how blank cells are plotted on the chart by show_blanks_as. The default value is gap. The options that can be set are: // @@ -750,18 +750,19 @@ func parseChartOptions(opts string) (*chartOptions, error) { // reverse_order // maximum // minimum -// number_font +// font // // The properties of y_axis that can be set are: // // none // major_grid_lines // minor_grid_lines +// major_unit // tick_label_skip // reverse_order // maximum // minimum -// number_font +// font // // none: Disable axes. // @@ -779,7 +780,7 @@ func parseChartOptions(opts string) (*chartOptions, error) { // // minimum: Specifies that the fixed minimum, 0 is auto. The minimum property is optional. The default value is auto. // -// number_font: Specifies that the font of the horizontal and vertical axis. The properties of number_font that can be set are: +// font: Specifies that the font of the horizontal and vertical axis. The properties of font that can be set are: // // bold // italic diff --git a/chart_test.go b/chart_test.go index a0f7156..6d40b44 100644 --- a/chart_test.go +++ b/chart_test.go @@ -116,7 +116,7 @@ func TestAddChart(t *testing.T) { // Test add chart on not exists worksheet. assert.EqualError(t, f.AddChart("SheetN", "P1", "{}"), "sheet SheetN does not exist") - assert.NoError(t, f.AddChart("Sheet1", "P1", `{"type":"col","series":[{"name":"Sheet1!$A$30","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$30:$D$30"},{"name":"Sheet1!$A$31","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$31:$D$31"},{"name":"Sheet1!$A$32","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$32:$D$32"},{"name":"Sheet1!$A$33","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$33:$D$33"},{"name":"Sheet1!$A$34","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$34:$D$34"},{"name":"Sheet1!$A$35","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$35:$D$35"},{"name":"Sheet1!$A$36","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$36:$D$36"},{"name":"Sheet1!$A$37","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$37:$D$37"}],"format":{"x_scale":1.0,"y_scale":1.0,"x_offset":15,"y_offset":10,"print_obj":true,"lock_aspect_ratio":false,"locked":false},"legend":{"none":true,"show_legend_key":true},"title":{"name":"2D Column Chart"},"plotarea":{"show_bubble_size":true,"show_cat_name":false,"show_leader_lines":false,"show_percent":true,"show_series_name":true,"show_val":true},"show_blanks_as":"zero","x_axis":{"number_font":{"bold":true,"italic":true,"underline":"dbl","color":"#000000"}},"y_axis":{"number_font":{"bold":false,"italic":false,"underline":"sng","color":"#777777"}}}`)) + assert.NoError(t, f.AddChart("Sheet1", "P1", `{"type":"col","series":[{"name":"Sheet1!$A$30","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$30:$D$30"},{"name":"Sheet1!$A$31","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$31:$D$31"},{"name":"Sheet1!$A$32","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$32:$D$32"},{"name":"Sheet1!$A$33","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$33:$D$33"},{"name":"Sheet1!$A$34","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$34:$D$34"},{"name":"Sheet1!$A$35","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$35:$D$35"},{"name":"Sheet1!$A$36","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$36:$D$36"},{"name":"Sheet1!$A$37","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$37:$D$37"}],"format":{"x_scale":1.0,"y_scale":1.0,"x_offset":15,"y_offset":10,"print_obj":true,"lock_aspect_ratio":false,"locked":false},"legend":{"none":true,"show_legend_key":true},"title":{"name":"2D Column Chart"},"plotarea":{"show_bubble_size":true,"show_cat_name":false,"show_leader_lines":false,"show_percent":true,"show_series_name":true,"show_val":true},"show_blanks_as":"zero","x_axis":{"font":{"bold":true,"italic":true,"underline":"dbl","color":"#000000"}},"y_axis":{"font":{"bold":false,"italic":false,"underline":"sng","color":"#777777"}}}`)) assert.NoError(t, f.AddChart("Sheet1", "X1", `{"type":"colStacked","series":[{"name":"Sheet1!$A$30","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$30:$D$30"},{"name":"Sheet1!$A$31","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$31:$D$31"},{"name":"Sheet1!$A$32","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$32:$D$32"},{"name":"Sheet1!$A$33","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$33:$D$33"},{"name":"Sheet1!$A$34","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$34:$D$34"},{"name":"Sheet1!$A$35","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$35:$D$35"},{"name":"Sheet1!$A$36","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$36:$D$36"},{"name":"Sheet1!$A$37","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$37:$D$37"}],"format":{"x_scale":1.0,"y_scale":1.0,"x_offset":15,"y_offset":10,"print_obj":true,"lock_aspect_ratio":false,"locked":false},"legend":{"position":"left","show_legend_key":false},"title":{"name":"2D Stacked Column Chart"},"plotarea":{"show_bubble_size":true,"show_cat_name":false,"show_leader_lines":false,"show_percent":true,"show_series_name":true,"show_val":true},"show_blanks_as":"zero"}`)) assert.NoError(t, f.AddChart("Sheet1", "P16", `{"type":"colPercentStacked","series":[{"name":"Sheet1!$A$30","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$30:$D$30"},{"name":"Sheet1!$A$31","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$31:$D$31"},{"name":"Sheet1!$A$32","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$32:$D$32"},{"name":"Sheet1!$A$33","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$33:$D$33"},{"name":"Sheet1!$A$34","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$34:$D$34"},{"name":"Sheet1!$A$35","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$35:$D$35"},{"name":"Sheet1!$A$36","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$36:$D$36"},{"name":"Sheet1!$A$37","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$37:$D$37"}],"format":{"x_scale":1.0,"y_scale":1.0,"x_offset":15,"y_offset":10,"print_obj":true,"lock_aspect_ratio":false,"locked":false},"legend":{"position":"left","show_legend_key":false},"title":{"name":"100% Stacked Column Chart"},"plotarea":{"show_bubble_size":true,"show_cat_name":false,"show_leader_lines":false,"show_percent":true,"show_series_name":true,"show_val":true},"show_blanks_as":"zero"}`)) assert.NoError(t, f.AddChart("Sheet1", "X16", `{"type":"col3DClustered","series":[{"name":"Sheet1!$A$30","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$30:$D$30"},{"name":"Sheet1!$A$31","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$31:$D$31"},{"name":"Sheet1!$A$32","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$32:$D$32"},{"name":"Sheet1!$A$33","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$33:$D$33"},{"name":"Sheet1!$A$34","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$34:$D$34"},{"name":"Sheet1!$A$35","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$35:$D$35"},{"name":"Sheet1!$A$36","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$36:$D$36"},{"name":"Sheet1!$A$37","categories":"Sheet1!$B$29:$D$29","values":"Sheet1!$B$37:$D$37"}],"format":{"x_scale":1.0,"y_scale":1.0,"x_offset":15,"y_offset":10,"print_obj":true,"lock_aspect_ratio":false,"locked":false},"legend":{"position":"bottom","show_legend_key":false},"title":{"name":"3D Clustered Column Chart"},"plotarea":{"show_bubble_size":true,"show_cat_name":false,"show_leader_lines":false,"show_percent":true,"show_series_name":true,"show_val":true},"show_blanks_as":"zero"}`)) @@ -1177,14 +1177,14 @@ func (f *File) drawPlotAreaTxPr(opts *chartAxisOptions) *cTxPr { }, } if opts != nil { - cTxPr.P.PPr.DefRPr.B = opts.NumFont.Bold - cTxPr.P.PPr.DefRPr.I = opts.NumFont.Italic - if idx := inStrSlice(supportedDrawingUnderlineTypes, opts.NumFont.Underline, true); idx != -1 { + cTxPr.P.PPr.DefRPr.B = opts.Font.Bold + cTxPr.P.PPr.DefRPr.I = opts.Font.Italic + if idx := inStrSlice(supportedDrawingUnderlineTypes, opts.Font.Underline, true); idx != -1 { cTxPr.P.PPr.DefRPr.U = supportedDrawingUnderlineTypes[idx] } - if opts.NumFont.Color != "" { + if opts.Font.Color != "" { cTxPr.P.PPr.DefRPr.SolidFill.SchemeClr = nil - cTxPr.P.PPr.DefRPr.SolidFill.SrgbClr = &attrValString{Val: stringPtr(strings.ReplaceAll(strings.ToUpper(opts.NumFont.Color), "#", ""))} + cTxPr.P.PPr.DefRPr.SolidFill.SrgbClr = &attrValString{Val: stringPtr(strings.ReplaceAll(strings.ToUpper(opts.Font.Color), "#", ""))} } } return cTxPr @@ -2084,21 +2084,42 @@ func (f *File) getFontID(styleSheet *xlsxStyleSheet, style *Style) (fontID int) return } +// newFontColor set font color by given styles. +func newFontColor(font *Font) *xlsxColor { + var fontColor *xlsxColor + prepareFontColor := func() { + if fontColor != nil { + return + } + fontColor = &xlsxColor{} + } + if font.Color != "" { + prepareFontColor() + fontColor.RGB = getPaletteColor(font.Color) + } + if font.ColorTheme != nil { + prepareFontColor() + fontColor.Theme = font.ColorTheme + } + if font.ColorTint != 0 { + prepareFontColor() + fontColor.Tint = font.ColorTint + } + return fontColor +} + // newFont provides a function to add font style by given cell format // settings. func (f *File) newFont(style *Style) *xlsxFont { if style.Font.Size < MinFontSize { style.Font.Size = 11 } - if style.Font.Color == "" { - style.Font.Color = "#000000" - } fnt := xlsxFont{ Sz: &attrValFloat{Val: float64Ptr(style.Font.Size)}, - Color: &xlsxColor{RGB: getPaletteColor(style.Font.Color)}, Name: &attrValString{Val: stringPtr(style.Font.Family)}, Family: &attrValInt{Val: intPtr(2)}, } + fnt.Color = newFontColor(style.Font) if style.Font.Bold { fnt.B = &attrValBool{Val: &style.Font.Bold} } diff --git a/xmlChart.go b/xmlChart.go index 27a790e..2ebcdef 100644 --- a/xmlChart.go +++ b/xmlChart.go @@ -476,7 +476,7 @@ type cNumCache struct { PtCount *attrValInt `xml:"ptCount"` } -// cDLbls (Data Lables) directly maps the dLbls element. This element serves +// cDLbls (Data Labels) directly maps the dLbls element. This element serves // as a root element that specifies the settings for the data labels for an // entire series or the entire chart. It contains child elements that specify // the specific formatting and positioning settings. @@ -538,7 +538,7 @@ type chartAxisOptions struct { Maximum *float64 `json:"maximum"` Minimum *float64 `json:"minimum"` NumFormat string `json:"number_format"` - NumFont Font `json:"number_font"` + Font Font `json:"font"` LogBase float64 `json:"logbase"` NameLayout layoutOptions `json:"name_layout"` } diff --git a/xmlStyles.go b/xmlStyles.go index 0000d45..e35dbdd 100644 --- a/xmlStyles.go +++ b/xmlStyles.go @@ -334,14 +334,16 @@ type Border struct { // Font directly maps the font settings of the fonts. type Font struct { - Bold bool `json:"bold"` - Italic bool `json:"italic"` - Underline string `json:"underline"` - Family string `json:"family"` - Size float64 `json:"size"` - Strike bool `json:"strike"` - Color string `json:"color"` - VertAlign string `json:"vertAlign"` + Bold bool `json:"bold"` + Italic bool `json:"italic"` + Underline string `json:"underline"` + Family string `json:"family"` + Size float64 `json:"size"` + Strike bool `json:"strike"` + Color string `json:"color"` + ColorTheme *int `json:"color_theme"` + ColorTint float64 `json:"color_tint"` + VertAlign string `json:"vertAlign"` } // Fill directly maps the fill settings of the cells. |