From 776dff179ccb07a66653281bdb386792ef6d73be Mon Sep 17 00:00:00 2001 From: tanszhe <1018595261@qq.com> Date: Mon, 18 Mar 2024 14:10:35 +0800 Subject: [PATCH] This closes #1847, support apply number format with alignment --- excelize_test.go | 10 +++++----- go.mod | 6 +++--- go.sum | 8 ++++++++ numfmt.go | 29 +++++++++++++++++++++++------ numfmt_test.go | 13 +++++++++---- 5 files changed, 48 insertions(+), 18 deletions(-) diff --git a/excelize_test.go b/excelize_test.go index 9879302648..95f0b41fa3 100644 --- a/excelize_test.go +++ b/excelize_test.go @@ -742,11 +742,11 @@ func TestSetCellStyleNumberFormat(t *testing.T) { idxTbl := []int{0, 1, 2, 3, 4, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49} value := []string{"37947.7500001", "-37947.7500001", "0.007", "2.1", "String"} expected := [][]string{ - {"37947.7500001", "37948", "37947.75", "37,948", "37,947.75", "3794775%", "3794775.00%", "3.79E+04", "37947 3/4", "37947 3/4", "11-22-03", "22-Nov-03", "22-Nov", "Nov-03", "6:00 PM", "6:00:00 PM", "18:00", "18:00:00", "11/22/03 18:00", "37,948 ", "37,948 ", "37,947.75 ", "37,947.75 ", "37,948", "$37,948", "37,947.75", "$37,947.75", "00:00", "910746:00:00", "00:00.0", "37947.7500001", "37947.7500001"}, - {"-37947.7500001", "-37948", "-37947.75", "-37,948", "-37,947.75", "-3794775%", "-3794775.00%", "-3.79E+04", "-37947 3/4", "-37947 3/4", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "(37,948)", "(37,948)", "(37,947.75)", "(37,947.75)", "(37,948)", "$(37,948)", "(37,947.75)", "$(37,947.75)", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001"}, - {"0.007", "0", "0.01", "0", "0.01", "1%", "0.70%", "7.00E-03", "0 ", "0 ", "12-30-99", "30-Dec-99", "30-Dec", "Dec-99", "12:10 AM", "12:10:05 AM", "00:10", "00:10:05", "12/30/99 00:10", "0 ", "0 ", "0.01 ", "0.01 ", "0", "$0", "0.01", "$0.01", "10:05", "0:10:05", "10:04.8", "0.007", "0.007"}, - {"2.1", "2", "2.10", "2", "2.10", "210%", "210.00%", "2.10E+00", "2 1/9", "2 1/10", "01-01-00", "1-Jan-00", "1-Jan", "Jan-00", "2:24 AM", "2:24:00 AM", "02:24", "02:24:00", "1/1/00 02:24", "2 ", "2 ", "2.10 ", "2.10 ", "2", "$2", "2.10", "$2.10", "24:00", "50:24:00", "24:00.0", "2.1", "2.1"}, - {"String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String"}, + {"37947.75", "37948", "37947.75", "37,948", "37,947.75", "3794775%", "3794775.00%", "3.79E+04", "37947 3/4", "37947 3/4", "11-22-03", "22-Nov-03", "22-Nov", "Nov-03", "6:00 PM", "6:00:00 PM", "18:00", "18:00:00", "11/22/03 18:00", "37,948 ", "37,948 ", "37,947.75 ", "37,947.75 ", " 37,948 ", " $37,948 ", " 37,947.75 ", " $37,947.75 ", "00:00", "910746:00:00", "00:00.0", "37947.7500001", "37947.7500001"}, + {"-37947.75", "-37948", "-37947.75", "-37,948", "-37,947.75", "-3794775%", "-3794775.00%", "-3.79E+04", "-37947 3/4", "-37947 3/4", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "(37,948)", "(37,948)", "(37,947.75)", "(37,947.75)", " (37,948)", " $(37,948)", " (37,947.75)", " $(37,947.75)", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001", "-37947.7500001"}, + {"0.007", "0", "0.01", "0", "0.01", "1%", "0.70%", "7.00E-03", "0 ", "0 ", "12-30-99", "30-Dec-99", "30-Dec", "Dec-99", "12:10 AM", "12:10:05 AM", "00:10", "00:10:05", "12/30/99 00:10", "0 ", "0 ", "0.01 ", "0.01 ", " 0 ", " $0 ", " 0.01 ", " $0.01 ", "10:05", "0:10:05", "10:04.8", "0.007", "0.007"}, + {"2.1", "2", "2.10", "2", "2.10", "210%", "210.00%", "2.10E+00", "2 1/9", "2 1/10", "01-01-00", "1-Jan-00", "1-Jan", "Jan-00", "2:24 AM", "2:24:00 AM", "02:24", "02:24:00", "1/1/00 02:24", "2 ", "2 ", "2.10 ", "2.10 ", " 2 ", " $2 ", " 2.10 ", " $2.10 ", "24:00", "50:24:00", "24:00.0", "2.1", "2.1"}, + {"String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", "String", " String ", " String ", " String ", " String ", "String", "String", "String", "String", "String"}, } for c, v := range value { diff --git a/go.mod b/go.mod index 357b84e631..8c12fa1eb6 100644 --- a/go.mod +++ b/go.mod @@ -7,10 +7,10 @@ require ( github.com/richardlehane/mscfb v1.0.4 github.com/stretchr/testify v1.8.4 github.com/xuri/efp v0.0.0-20231025114914-d1ff6096ae53 - github.com/xuri/nfp v0.0.0-20230919160717-d98342af3f05 - golang.org/x/crypto v0.19.0 + github.com/xuri/nfp v0.0.0-20240318013403-ab9948c2c4a7 + golang.org/x/crypto v0.21.0 golang.org/x/image v0.14.0 - golang.org/x/net v0.21.0 + golang.org/x/net v0.22.0 golang.org/x/text v0.14.0 ) diff --git a/go.sum b/go.sum index 64de49a3e6..9c04edd934 100644 --- a/go.sum +++ b/go.sum @@ -15,12 +15,20 @@ github.com/xuri/efp v0.0.0-20231025114914-d1ff6096ae53 h1:Chd9DkqERQQuHpXjR/HSV1 github.com/xuri/efp v0.0.0-20231025114914-d1ff6096ae53/go.mod h1:ybY/Jr0T0GTCnYjKqmdwxyxn2BQf2RcQIIvex5QldPI= github.com/xuri/nfp v0.0.0-20230919160717-d98342af3f05 h1:qhbILQo1K3mphbwKh1vNm4oGezE1eF9fQWmNiIpSfI4= github.com/xuri/nfp v0.0.0-20230919160717-d98342af3f05/go.mod h1:WwHg+CVyzlv/TX9xqBFXEZAuxOPxn2k1GNHwG41IIUQ= +github.com/xuri/nfp v0.0.0-20240316161844-5bacf1a74267 h1:p0lQ21ogqdVWcdXpqSlD7gu/3whO1YWNiOaPJNBfunU= +github.com/xuri/nfp v0.0.0-20240316161844-5bacf1a74267/go.mod h1:WwHg+CVyzlv/TX9xqBFXEZAuxOPxn2k1GNHwG41IIUQ= +github.com/xuri/nfp v0.0.0-20240318013403-ab9948c2c4a7 h1:hPVCafDV85blFTabnqKgNhDCkJX25eik94Si9cTER4A= +github.com/xuri/nfp v0.0.0-20240318013403-ab9948c2c4a7/go.mod h1:WwHg+CVyzlv/TX9xqBFXEZAuxOPxn2k1GNHwG41IIUQ= golang.org/x/crypto v0.19.0 h1:ENy+Az/9Y1vSrlrvBSyna3PITt4tiZLf7sgCjZBX7Wo= golang.org/x/crypto v0.19.0/go.mod h1:Iy9bg/ha4yyC70EfRS8jz+B6ybOBKMaSxLj6P6oBDfU= +golang.org/x/crypto v0.21.0 h1:X31++rzVUdKhX5sWmSOFZxx8UW/ldWx55cbf08iNAMA= +golang.org/x/crypto v0.21.0/go.mod h1:0BP7YvVV9gBbVKyeTG0Gyn+gZm94bibOW5BjDEYAOMs= golang.org/x/image v0.14.0 h1:tNgSxAFe3jC4uYqvZdTr84SZoM1KfwdC9SKIFrLjFn4= golang.org/x/image v0.14.0/go.mod h1:HUYqC05R2ZcZ3ejNQsIHQDQiwWM4JBqmm6MKANTp4LE= golang.org/x/net v0.21.0 h1:AQyQV4dYCvJ7vGmJyKki9+PBdyvhkSd8EIx/qb0AYv4= golang.org/x/net v0.21.0/go.mod h1:bIjVDfnllIU7BJ2DNgfnXvpSvtn8VRwhlsaeUTyUS44= +golang.org/x/net v0.22.0 h1:9sGLhx7iRIHEiX0oAJ3MRZMUCElJgy7Br1nO+AMN3Tc= +golang.org/x/net v0.22.0/go.mod h1:JKghWKKOSdJwpW2GEx0Ja7fmaKnMsbu+MWVZTokSYmg= golang.org/x/text v0.14.0 h1:ScX5w1eTa3QqT8oi6+ziP7dTV1S2+ALU0bI+0zXKWiQ= golang.org/x/text v0.14.0/go.mod h1:18ZOQIKpY8NJVqYksKHtTdi31H5itFRjB5/qKTNYzSU= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= diff --git a/numfmt.go b/numfmt.go index d37130b741..47f2d4a56f 100644 --- a/numfmt.go +++ b/numfmt.go @@ -682,6 +682,7 @@ var ( } // supportedTokenTypes list the supported number format token types currently. supportedTokenTypes = []string{ + nfp.TokenTypeAlignment, nfp.TokenSubTypeCurrencyString, nfp.TokenSubTypeLanguageInfo, nfp.TokenTypeColor, @@ -4797,14 +4798,14 @@ func format(value, numFmt string, date1904 bool, cellType CellType, opts *Option if nf.isNumeric { switch section.Type { case nfp.TokenSectionPositive: - return nf.positiveHandler() + return nf.alignmentHandler(nf.positiveHandler()) case nfp.TokenSectionNegative: - return nf.negativeHandler() + return nf.alignmentHandler(nf.negativeHandler()) default: - return nf.zeroHandler() + return nf.alignmentHandler(nf.zeroHandler()) } } - return nf.textHandler() + return nf.alignmentHandler(nf.textHandler()) } return value } @@ -5082,13 +5083,29 @@ func (nf *numberFormat) dateTimeHandler() string { return nf.printSwitchArgument(nf.result) } +// alignmentHandler will be handling alignment token for each number format +// selection for a number format expression. +func (nf *numberFormat) alignmentHandler(result string) string { + tokens := nf.section[nf.sectionIdx].Items + if len(tokens) == 0 { + return result + } + if tokens[0].TType == nfp.TokenTypeAlignment { + result = nfp.Whitespace + result + } + if l := len(tokens); tokens[l-1].TType == nfp.TokenTypeAlignment { + result += nfp.Whitespace + } + return result +} + // positiveHandler will be handling positive selection for a number format // expression. func (nf *numberFormat) positiveHandler() string { var fmtNum bool for _, token := range nf.section[nf.sectionIdx].Items { - if inStrSlice(supportedTokenTypes, token.TType, true) == -1 || token.TType == nfp.TokenTypeGeneral { - return nf.value + if token.TType == nfp.TokenTypeGeneral { + return strconv.FormatFloat(nf.number, 'G', 10, 64) } if inStrSlice(supportedNumberTokenTypes, token.TType, true) != -1 { fmtNum = true diff --git a/numfmt_test.go b/numfmt_test.go index b449feb44c..49e4fa03be 100644 --- a/numfmt_test.go +++ b/numfmt_test.go @@ -11,6 +11,9 @@ func TestNumFmt(t *testing.T) { for _, item := range [][]string{ {"123", "general", "123"}, {"-123", ";general", "-123"}, + {"43543.5448726851", "General", "43543.54487"}, + {"-43543.5448726851", "General", "-43543.54487"}, + {"1234567890.12345", "General", "1234567890"}, {"43528", "y", "19"}, {"43528", "Y", "19"}, {"43528", "yy", "19"}, @@ -3488,14 +3491,16 @@ func TestNumFmt(t *testing.T) { {"43543.503206018519", "[$-F400]h:mm:ss AM/PM", "12:04:37 PM"}, {"text_", "General", "text_"}, {"text_", "\"=====\"@@@\"--\"@\"----\"", "=====text_text_text_--text_----"}, - {"0.0450685976001E+21", "0_);[Red]\\(0\\)", "45068597600100000000"}, - {"8.0450685976001E+21", "0_);[Red]\\(0\\)", "8045068597600100000000"}, - {"8.0450685976001E-21", "0_);[Red]\\(0\\)", "0"}, - {"8.04506", "0_);[Red]\\(0\\)", "8"}, + {"0.0450685976001E+21", "0_);[Red]\\(0\\)", "45068597600100000000 "}, + {"8.0450685976001E+21", "0_);[Red]\\(0\\)", "8045068597600100000000 "}, + {"8.0450685976001E-21", "0_);[Red]\\(0\\)", "0 "}, + {"8.04506", "0_);[Red]\\(0\\)", "8 "}, {"-0.0450685976001E+21", "0_);[Red]\\(0\\)", "(45068597600100000000)"}, {"-8.0450685976001E+21", "0_);[Red]\\(0\\)", "(8045068597600100000000)"}, {"-8.0450685976001E-21", "0_);[Red]\\(0\\)", "(0)"}, {"-8.04506", "0_);[Red]\\(0\\)", "(8)"}, + {"-8.04506", "$#,##0.00_);[Red]($#,##0.00)", "($8.05)"}, + {"43543.5448726851", `_("$"* #,##0.00_);_("$"* \(#,##0.00\);_("$"* "-"??_);_(@_)`, " $43,543.54 "}, {"1234.5678", "0", "1235"}, {"1234.5678", "0.00", "1234.57"}, {"1234.5678", "#,##0", "1,235"},