Initial QSfera import

This commit is contained in:
Курнат Андрей
2026-06-07 10:20:04 +03:00
commit 2315f25754
16485 changed files with 4826827 additions and 0 deletions
@@ -0,0 +1,24 @@
# Compiled Object files, Static and Dynamic libs (Shared Objects)
*.o
*.a
*.so
# Folders
_obj
_test
# Architecture specific extensions/prefixes
*.[568vq]
[568vq].out
*.cgo1.go
*.cgo2.c
_cgo_defun.c
_cgo_gotypes.go
_cgo_export.*
_testmain.go
*.exe
*.test
*.prof
+26
View File
@@ -0,0 +1,26 @@
language: go
go:
- 1.13.1
- tip
matrix:
allow_failures:
- go: tip
notifications:
email:
recipients: dean.karn@gmail.com
on_success: change
on_failure: always
before_install:
- go install github.com/mattn/goveralls
# Only clone the most recent commit.
git:
depth: 1
script:
- go test -v -race -covermode=atomic -coverprofile=coverage.coverprofile ./...
after_success: |
goveralls -coverprofile=coverage.coverprofile -service travis-ci -repotoken $COVERALLS_TOKEN
+21
View File
@@ -0,0 +1,21 @@
The MIT License (MIT)
Copyright (c) 2016 Go Playground
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
+170
View File
@@ -0,0 +1,170 @@
## locales
<img align="right" src="https://raw.githubusercontent.com/go-playground/locales/master/logo.png">![Project status](https://img.shields.io/badge/version-0.14.1-green.svg)
[![Build Status](https://travis-ci.org/go-playground/locales.svg?branch=master)](https://travis-ci.org/go-playground/locales)
[![GoDoc](https://godoc.org/github.com/go-playground/locales?status.svg)](https://godoc.org/github.com/go-playground/locales)
![License](https://img.shields.io/dub/l/vibe-d.svg)
Locales is a set of locales generated from the [Unicode CLDR Project](http://cldr.unicode.org/) which can be used independently or within
an i18n package; these were built for use with, but not exclusive to, [Universal Translator](https://github.com/go-playground/universal-translator).
Features
--------
- [x] Rules generated from the latest [CLDR](http://cldr.unicode.org/index/downloads) data, v36.0.1
- [x] Contains Cardinal, Ordinal and Range Plural Rules
- [x] Contains Month, Weekday and Timezone translations built in
- [x] Contains Date & Time formatting functions
- [x] Contains Number, Currency, Accounting and Percent formatting functions
- [x] Supports the "Gregorian" calendar only ( my time isn't unlimited, had to draw the line somewhere )
Full Tests
--------------------
I could sure use your help adding tests for every locale, it is a huge undertaking and I just don't have the free time to do it all at the moment;
any help would be **greatly appreciated!!!!** please see [issue](https://github.com/go-playground/locales/issues/1) for details.
Installation
-----------
Use go get
```shell
go get github.com/go-playground/locales
```
NOTES
--------
You'll notice most return types are []byte, this is because most of the time the results will be concatenated with a larger body
of text and can avoid some allocations if already appending to a byte array, otherwise just cast as string.
Usage
-------
```go
package main
import (
"fmt"
"time"
"github.com/go-playground/locales/currency"
"github.com/go-playground/locales/en_CA"
)
func main() {
loc, _ := time.LoadLocation("America/Toronto")
datetime := time.Date(2016, 02, 03, 9, 0, 1, 0, loc)
l := en_CA.New()
// Dates
fmt.Println(l.FmtDateFull(datetime))
fmt.Println(l.FmtDateLong(datetime))
fmt.Println(l.FmtDateMedium(datetime))
fmt.Println(l.FmtDateShort(datetime))
// Times
fmt.Println(l.FmtTimeFull(datetime))
fmt.Println(l.FmtTimeLong(datetime))
fmt.Println(l.FmtTimeMedium(datetime))
fmt.Println(l.FmtTimeShort(datetime))
// Months Wide
fmt.Println(l.MonthWide(time.January))
fmt.Println(l.MonthWide(time.February))
fmt.Println(l.MonthWide(time.March))
// ...
// Months Abbreviated
fmt.Println(l.MonthAbbreviated(time.January))
fmt.Println(l.MonthAbbreviated(time.February))
fmt.Println(l.MonthAbbreviated(time.March))
// ...
// Months Narrow
fmt.Println(l.MonthNarrow(time.January))
fmt.Println(l.MonthNarrow(time.February))
fmt.Println(l.MonthNarrow(time.March))
// ...
// Weekdays Wide
fmt.Println(l.WeekdayWide(time.Sunday))
fmt.Println(l.WeekdayWide(time.Monday))
fmt.Println(l.WeekdayWide(time.Tuesday))
// ...
// Weekdays Abbreviated
fmt.Println(l.WeekdayAbbreviated(time.Sunday))
fmt.Println(l.WeekdayAbbreviated(time.Monday))
fmt.Println(l.WeekdayAbbreviated(time.Tuesday))
// ...
// Weekdays Short
fmt.Println(l.WeekdayShort(time.Sunday))
fmt.Println(l.WeekdayShort(time.Monday))
fmt.Println(l.WeekdayShort(time.Tuesday))
// ...
// Weekdays Narrow
fmt.Println(l.WeekdayNarrow(time.Sunday))
fmt.Println(l.WeekdayNarrow(time.Monday))
fmt.Println(l.WeekdayNarrow(time.Tuesday))
// ...
var f64 float64
f64 = -10356.4523
// Number
fmt.Println(l.FmtNumber(f64, 2))
// Currency
fmt.Println(l.FmtCurrency(f64, 2, currency.CAD))
fmt.Println(l.FmtCurrency(f64, 2, currency.USD))
// Accounting
fmt.Println(l.FmtAccounting(f64, 2, currency.CAD))
fmt.Println(l.FmtAccounting(f64, 2, currency.USD))
f64 = 78.12
// Percent
fmt.Println(l.FmtPercent(f64, 0))
// Plural Rules for locale, so you know what rules you must cover
fmt.Println(l.PluralsCardinal())
fmt.Println(l.PluralsOrdinal())
// Cardinal Plural Rules
fmt.Println(l.CardinalPluralRule(1, 0))
fmt.Println(l.CardinalPluralRule(1.0, 0))
fmt.Println(l.CardinalPluralRule(1.0, 1))
fmt.Println(l.CardinalPluralRule(3, 0))
// Ordinal Plural Rules
fmt.Println(l.OrdinalPluralRule(21, 0)) // 21st
fmt.Println(l.OrdinalPluralRule(22, 0)) // 22nd
fmt.Println(l.OrdinalPluralRule(33, 0)) // 33rd
fmt.Println(l.OrdinalPluralRule(34, 0)) // 34th
// Range Plural Rules
fmt.Println(l.RangePluralRule(1, 0, 1, 0)) // 1-1
fmt.Println(l.RangePluralRule(1, 0, 2, 0)) // 1-2
fmt.Println(l.RangePluralRule(5, 0, 8, 0)) // 5-8
}
```
NOTES:
-------
These rules were generated from the [Unicode CLDR Project](http://cldr.unicode.org/), if you encounter any issues
I strongly encourage contributing to the CLDR project to get the locale information corrected and the next time
these locales are regenerated the fix will come with.
I do however realize that time constraints are often important and so there are two options:
1. Create your own locale, copy, paste and modify, and ensure it complies with the `Translator` interface.
2. Add an exception in the locale generation code directly and once regenerated, fix will be in place.
Please to not make fixes inside the locale files, they WILL get overwritten when the locales are regenerated.
License
------
Distributed under MIT License, please see license file in code for more details.
+311
View File
@@ -0,0 +1,311 @@
package currency
// Type is the currency type associated with the locales currency enum
type Type int
// locale currencies
const (
ADP Type = iota
AED
AFA
AFN
ALK
ALL
AMD
ANG
AOA
AOK
AON
AOR
ARA
ARL
ARM
ARP
ARS
ATS
AUD
AWG
AZM
AZN
BAD
BAM
BAN
BBD
BDT
BEC
BEF
BEL
BGL
BGM
BGN
BGO
BHD
BIF
BMD
BND
BOB
BOL
BOP
BOV
BRB
BRC
BRE
BRL
BRN
BRR
BRZ
BSD
BTN
BUK
BWP
BYB
BYN
BYR
BZD
CAD
CDF
CHE
CHF
CHW
CLE
CLF
CLP
CNH
CNX
CNY
COP
COU
CRC
CSD
CSK
CUC
CUP
CVE
CYP
CZK
DDM
DEM
DJF
DKK
DOP
DZD
ECS
ECV
EEK
EGP
ERN
ESA
ESB
ESP
ETB
EUR
FIM
FJD
FKP
FRF
GBP
GEK
GEL
GHC
GHS
GIP
GMD
GNF
GNS
GQE
GRD
GTQ
GWE
GWP
GYD
HKD
HNL
HRD
HRK
HTG
HUF
IDR
IEP
ILP
ILR
ILS
INR
IQD
IRR
ISJ
ISK
ITL
JMD
JOD
JPY
KES
KGS
KHR
KMF
KPW
KRH
KRO
KRW
KWD
KYD
KZT
LAK
LBP
LKR
LRD
LSL
LTL
LTT
LUC
LUF
LUL
LVL
LVR
LYD
MAD
MAF
MCF
MDC
MDL
MGA
MGF
MKD
MKN
MLF
MMK
MNT
MOP
MRO
MRU
MTL
MTP
MUR
MVP
MVR
MWK
MXN
MXP
MXV
MYR
MZE
MZM
MZN
NAD
NGN
NIC
NIO
NLG
NOK
NPR
NZD
OMR
PAB
PEI
PEN
PES
PGK
PHP
PKR
PLN
PLZ
PTE
PYG
QAR
RHD
ROL
RON
RSD
RUB
RUR
RWF
SAR
SBD
SCR
SDD
SDG
SDP
SEK
SGD
SHP
SIT
SKK
SLL
SOS
SRD
SRG
SSP
STD
STN
SUR
SVC
SYP
SZL
THB
TJR
TJS
TMM
TMT
TND
TOP
TPE
TRL
TRY
TTD
TWD
TZS
UAH
UAK
UGS
UGX
USD
USN
USS
UYI
UYP
UYU
UYW
UZS
VEB
VEF
VES
VND
VNN
VUV
WST
XAF
XAG
XAU
XBA
XBB
XBC
XBD
XCD
XDR
XEU
XFO
XFU
XOF
XPD
XPF
XPT
XRE
XSU
XTS
XUA
XXX
YDD
YER
YUD
YUM
YUN
YUR
ZAL
ZAR
ZMK
ZMW
ZRN
ZRZ
ZWD
ZWL
ZWR
)
+650
View File
@@ -0,0 +1,650 @@
package en
import (
"math"
"strconv"
"time"
"github.com/go-playground/locales"
"github.com/go-playground/locales/currency"
)
type en struct {
locale string
pluralsCardinal []locales.PluralRule
pluralsOrdinal []locales.PluralRule
pluralsRange []locales.PluralRule
decimal string
group string
minus string
percent string
perMille string
timeSeparator string
inifinity string
currencies []string // idx = enum of currency code
currencyNegativePrefix string
currencyNegativeSuffix string
monthsAbbreviated []string
monthsNarrow []string
monthsWide []string
daysAbbreviated []string
daysNarrow []string
daysShort []string
daysWide []string
periodsAbbreviated []string
periodsNarrow []string
periodsShort []string
periodsWide []string
erasAbbreviated []string
erasNarrow []string
erasWide []string
timezones map[string]string
}
// New returns a new instance of translator for the 'en' locale
func New() locales.Translator {
return &en{
locale: "en",
pluralsCardinal: []locales.PluralRule{2, 6},
pluralsOrdinal: []locales.PluralRule{2, 3, 4, 6},
pluralsRange: []locales.PluralRule{6},
decimal: ".",
group: ",",
minus: "-",
percent: "%",
perMille: "‰",
timeSeparator: ":",
inifinity: "∞",
currencies: []string{"ADP", "AED", "AFA", "AFN", "ALK", "ALL", "AMD", "ANG", "AOA", "AOK", "AON", "AOR", "ARA", "ARL", "ARM", "ARP", "ARS", "ATS", "AUD", "AWG", "AZM", "AZN", "BAD", "BAM", "BAN", "BBD", "BDT", "BEC", "BEF", "BEL", "BGL", "BGM", "BGN", "BGO", "BHD", "BIF", "BMD", "BND", "BOB", "BOL", "BOP", "BOV", "BRB", "BRC", "BRE", "BRL", "BRN", "BRR", "BRZ", "BSD", "BTN", "BUK", "BWP", "BYB", "BYN", "BYR", "BZD", "CAD", "CDF", "CHE", "CHF", "CHW", "CLE", "CLF", "CLP", "CNH", "CNX", "CNY", "COP", "COU", "CRC", "CSD", "CSK", "CUC", "CUP", "CVE", "CYP", "CZK", "DDM", "DEM", "DJF", "DKK", "DOP", "DZD", "ECS", "ECV", "EEK", "EGP", "ERN", "ESA", "ESB", "ESP", "ETB", "EUR", "FIM", "FJD", "FKP", "FRF", "GBP", "GEK", "GEL", "GHC", "GHS", "GIP", "GMD", "GNF", "GNS", "GQE", "GRD", "GTQ", "GWE", "GWP", "GYD", "HKD", "HNL", "HRD", "HRK", "HTG", "HUF", "IDR", "IEP", "ILP", "ILR", "ILS", "INR", "IQD", "IRR", "ISJ", "ISK", "ITL", "JMD", "JOD", "¥", "KES", "KGS", "KHR", "KMF", "KPW", "KRH", "KRO", "KRW", "KWD", "KYD", "KZT", "LAK", "LBP", "LKR", "LRD", "LSL", "LTL", "LTT", "LUC", "LUF", "LUL", "LVL", "LVR", "LYD", "MAD", "MAF", "MCF", "MDC", "MDL", "MGA", "MGF", "MKD", "MKN", "MLF", "MMK", "MNT", "MOP", "MRO", "MRU", "MTL", "MTP", "MUR", "MVP", "MVR", "MWK", "MXN", "MXP", "MXV", "MYR", "MZE", "MZM", "MZN", "NAD", "NGN", "NIC", "NIO", "NLG", "NOK", "NPR", "NZD", "OMR", "PAB", "PEI", "PEN", "PES", "PGK", "PHP", "PKR", "PLN", "PLZ", "PTE", "PYG", "QAR", "RHD", "ROL", "RON", "RSD", "RUB", "RUR", "RWF", "SAR", "SBD", "SCR", "SDD", "SDG", "SDP", "SEK", "SGD", "SHP", "SIT", "SKK", "SLL", "SOS", "SRD", "SRG", "SSP", "STD", "STN", "SUR", "SVC", "SYP", "SZL", "THB", "TJR", "TJS", "TMM", "TMT", "TND", "TOP", "TPE", "TRL", "TRY", "TTD", "TWD", "TZS", "UAH", "UAK", "UGS", "UGX", "$", "USN", "USS", "UYI", "UYP", "UYU", "UYW", "UZS", "VEB", "VEF", "VES", "VND", "VNN", "VUV", "WST", "XAF", "XAG", "XAU", "XBA", "XBB", "XBC", "XBD", "XCD", "XDR", "XEU", "XFO", "XFU", "XOF", "XPD", "XPF", "XPT", "XRE", "XSU", "XTS", "XUA", "XXX", "YDD", "YER", "YUD", "YUM", "YUN", "YUR", "ZAL", "ZAR", "ZMK", "ZMW", "ZRN", "ZRZ", "ZWD", "ZWL", "ZWR"},
currencyNegativePrefix: "(",
currencyNegativeSuffix: ")",
monthsAbbreviated: []string{"", "Jan", "Feb", "Mar", "Apr", "May", "Jun", "Jul", "Aug", "Sep", "Oct", "Nov", "Dec"},
monthsNarrow: []string{"", "J", "F", "M", "A", "M", "J", "J", "A", "S", "O", "N", "D"},
monthsWide: []string{"", "January", "February", "March", "April", "May", "June", "July", "August", "September", "October", "November", "December"},
daysAbbreviated: []string{"Sun", "Mon", "Tue", "Wed", "Thu", "Fri", "Sat"},
daysNarrow: []string{"S", "M", "T", "W", "T", "F", "S"},
daysShort: []string{"Su", "Mo", "Tu", "We", "Th", "Fr", "Sa"},
daysWide: []string{"Sunday", "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday"},
periodsAbbreviated: []string{"am", "pm"},
periodsNarrow: []string{"a", "p"},
periodsWide: []string{"am", "pm"},
erasAbbreviated: []string{"BC", "AD"},
erasNarrow: []string{"B", "A"},
erasWide: []string{"Before Christ", "Anno Domini"},
timezones: map[string]string{"ACDT": "Australian Central Daylight Time", "ACST": "Australian Central Standard Time", "ACWDT": "Australian Central Western Daylight Time", "ACWST": "Australian Central Western Standard Time", "ADT": "Atlantic Daylight Time", "AEDT": "Australian Eastern Daylight Time", "AEST": "Australian Eastern Standard Time", "AKDT": "Alaska Daylight Time", "AKST": "Alaska Standard Time", "ARST": "Argentina Summer Time", "ART": "Argentina Standard Time", "AST": "Atlantic Standard Time", "AWDT": "Australian Western Daylight Time", "AWST": "Australian Western Standard Time", "BOT": "Bolivia Time", "BT": "Bhutan Time", "CAT": "Central Africa Time", "CDT": "Central Daylight Time", "CHADT": "Chatham Daylight Time", "CHAST": "Chatham Standard Time", "CLST": "Chile Summer Time", "CLT": "Chile Standard Time", "COST": "Colombia Summer Time", "COT": "Colombia Standard Time", "CST": "Central Standard Time", "ChST": "Chamorro Standard Time", "EAT": "East Africa Time", "ECT": "Ecuador Time", "EDT": "Eastern Daylight Time", "EST": "Eastern Standard Time", "GFT": "French Guiana Time", "GMT": "Greenwich Mean Time", "GST": "Gulf Standard Time", "GYT": "Guyana Time", "HADT": "Hawaii-Aleutian Daylight Time", "HAST": "Hawaii-Aleutian Standard Time", "HAT": "Newfoundland Daylight Time", "HECU": "Cuba Daylight Time", "HEEG": "East Greenland Summer Time", "HENOMX": "Northwest Mexico Daylight Time", "HEOG": "West Greenland Summer Time", "HEPM": "St. Pierre & Miquelon Daylight Time", "HEPMX": "Mexican Pacific Daylight Time", "HKST": "Hong Kong Summer Time", "HKT": "Hong Kong Standard Time", "HNCU": "Cuba Standard Time", "HNEG": "East Greenland Standard Time", "HNNOMX": "Northwest Mexico Standard Time", "HNOG": "West Greenland Standard Time", "HNPM": "St. Pierre & Miquelon Standard Time", "HNPMX": "Mexican Pacific Standard Time", "HNT": "Newfoundland Standard Time", "IST": "India Standard Time", "JDT": "Japan Daylight Time", "JST": "Japan Standard Time", "LHDT": "Lord Howe Daylight Time", "LHST": "Lord Howe Standard Time", "MDT": "Mountain Daylight Time", "MESZ": "Central European Summer Time", "MEZ": "Central European Standard Time", "MST": "Mountain Standard Time", "MYT": "Malaysia Time", "NZDT": "New Zealand Daylight Time", "NZST": "New Zealand Standard Time", "OESZ": "Eastern European Summer Time", "OEZ": "Eastern European Standard Time", "PDT": "Pacific Daylight Time", "PST": "Pacific Standard Time", "SAST": "South Africa Standard Time", "SGT": "Singapore Standard Time", "SRT": "Suriname Time", "TMST": "Turkmenistan Summer Time", "TMT": "Turkmenistan Standard Time", "UYST": "Uruguay Summer Time", "UYT": "Uruguay Standard Time", "VET": "Venezuela Time", "WARST": "Western Argentina Summer Time", "WART": "Western Argentina Standard Time", "WAST": "West Africa Summer Time", "WAT": "West Africa Standard Time", "WESZ": "Western European Summer Time", "WEZ": "Western European Standard Time", "WIB": "Western Indonesia Time", "WIT": "Eastern Indonesia Time", "WITA": "Central Indonesia Time", "∅∅∅": "Brasilia Summer Time"},
}
}
// Locale returns the current translators string locale
func (en *en) Locale() string {
return en.locale
}
// PluralsCardinal returns the list of cardinal plural rules associated with 'en'
func (en *en) PluralsCardinal() []locales.PluralRule {
return en.pluralsCardinal
}
// PluralsOrdinal returns the list of ordinal plural rules associated with 'en'
func (en *en) PluralsOrdinal() []locales.PluralRule {
return en.pluralsOrdinal
}
// PluralsRange returns the list of range plural rules associated with 'en'
func (en *en) PluralsRange() []locales.PluralRule {
return en.pluralsRange
}
// CardinalPluralRule returns the cardinal PluralRule given 'num' and digits/precision of 'v' for 'en'
func (en *en) CardinalPluralRule(num float64, v uint64) locales.PluralRule {
n := math.Abs(num)
i := int64(n)
if i == 1 && v == 0 {
return locales.PluralRuleOne
}
return locales.PluralRuleOther
}
// OrdinalPluralRule returns the ordinal PluralRule given 'num' and digits/precision of 'v' for 'en'
func (en *en) OrdinalPluralRule(num float64, v uint64) locales.PluralRule {
n := math.Abs(num)
nMod100 := math.Mod(n, 100)
nMod10 := math.Mod(n, 10)
if nMod10 == 1 && nMod100 != 11 {
return locales.PluralRuleOne
} else if nMod10 == 2 && nMod100 != 12 {
return locales.PluralRuleTwo
} else if nMod10 == 3 && nMod100 != 13 {
return locales.PluralRuleFew
}
return locales.PluralRuleOther
}
// RangePluralRule returns the ordinal PluralRule given 'num1', 'num2' and digits/precision of 'v1' and 'v2' for 'en'
func (en *en) RangePluralRule(num1 float64, v1 uint64, num2 float64, v2 uint64) locales.PluralRule {
return locales.PluralRuleOther
}
// MonthAbbreviated returns the locales abbreviated month given the 'month' provided
func (en *en) MonthAbbreviated(month time.Month) string {
return en.monthsAbbreviated[month]
}
// MonthsAbbreviated returns the locales abbreviated months
func (en *en) MonthsAbbreviated() []string {
return en.monthsAbbreviated[1:]
}
// MonthNarrow returns the locales narrow month given the 'month' provided
func (en *en) MonthNarrow(month time.Month) string {
return en.monthsNarrow[month]
}
// MonthsNarrow returns the locales narrow months
func (en *en) MonthsNarrow() []string {
return en.monthsNarrow[1:]
}
// MonthWide returns the locales wide month given the 'month' provided
func (en *en) MonthWide(month time.Month) string {
return en.monthsWide[month]
}
// MonthsWide returns the locales wide months
func (en *en) MonthsWide() []string {
return en.monthsWide[1:]
}
// WeekdayAbbreviated returns the locales abbreviated weekday given the 'weekday' provided
func (en *en) WeekdayAbbreviated(weekday time.Weekday) string {
return en.daysAbbreviated[weekday]
}
// WeekdaysAbbreviated returns the locales abbreviated weekdays
func (en *en) WeekdaysAbbreviated() []string {
return en.daysAbbreviated
}
// WeekdayNarrow returns the locales narrow weekday given the 'weekday' provided
func (en *en) WeekdayNarrow(weekday time.Weekday) string {
return en.daysNarrow[weekday]
}
// WeekdaysNarrow returns the locales narrow weekdays
func (en *en) WeekdaysNarrow() []string {
return en.daysNarrow
}
// WeekdayShort returns the locales short weekday given the 'weekday' provided
func (en *en) WeekdayShort(weekday time.Weekday) string {
return en.daysShort[weekday]
}
// WeekdaysShort returns the locales short weekdays
func (en *en) WeekdaysShort() []string {
return en.daysShort
}
// WeekdayWide returns the locales wide weekday given the 'weekday' provided
func (en *en) WeekdayWide(weekday time.Weekday) string {
return en.daysWide[weekday]
}
// WeekdaysWide returns the locales wide weekdays
func (en *en) WeekdaysWide() []string {
return en.daysWide
}
// Decimal returns the decimal point of number
func (en *en) Decimal() string {
return en.decimal
}
// Group returns the group of number
func (en *en) Group() string {
return en.group
}
// Group returns the minus sign of number
func (en *en) Minus() string {
return en.minus
}
// FmtNumber returns 'num' with digits/precision of 'v' for 'en' and handles both Whole and Real numbers based on 'v'
func (en *en) FmtNumber(num float64, v uint64) string {
s := strconv.FormatFloat(math.Abs(num), 'f', int(v), 64)
l := len(s) + 2 + 1*len(s[:len(s)-int(v)-1])/3
count := 0
inWhole := v == 0
b := make([]byte, 0, l)
for i := len(s) - 1; i >= 0; i-- {
if s[i] == '.' {
b = append(b, en.decimal[0])
inWhole = true
continue
}
if inWhole {
if count == 3 {
b = append(b, en.group[0])
count = 1
} else {
count++
}
}
b = append(b, s[i])
}
if num < 0 {
b = append(b, en.minus[0])
}
// reverse
for i, j := 0, len(b)-1; i < j; i, j = i+1, j-1 {
b[i], b[j] = b[j], b[i]
}
return string(b)
}
// FmtPercent returns 'num' with digits/precision of 'v' for 'en' and handles both Whole and Real numbers based on 'v'
// NOTE: 'num' passed into FmtPercent is assumed to be in percent already
func (en *en) FmtPercent(num float64, v uint64) string {
s := strconv.FormatFloat(math.Abs(num), 'f', int(v), 64)
l := len(s) + 3
b := make([]byte, 0, l)
for i := len(s) - 1; i >= 0; i-- {
if s[i] == '.' {
b = append(b, en.decimal[0])
continue
}
b = append(b, s[i])
}
if num < 0 {
b = append(b, en.minus[0])
}
// reverse
for i, j := 0, len(b)-1; i < j; i, j = i+1, j-1 {
b[i], b[j] = b[j], b[i]
}
b = append(b, en.percent...)
return string(b)
}
// FmtCurrency returns the currency representation of 'num' with digits/precision of 'v' for 'en'
func (en *en) FmtCurrency(num float64, v uint64, currency currency.Type) string {
s := strconv.FormatFloat(math.Abs(num), 'f', int(v), 64)
symbol := en.currencies[currency]
l := len(s) + len(symbol) + 2 + 1*len(s[:len(s)-int(v)-1])/3
count := 0
inWhole := v == 0
b := make([]byte, 0, l)
for i := len(s) - 1; i >= 0; i-- {
if s[i] == '.' {
b = append(b, en.decimal[0])
inWhole = true
continue
}
if inWhole {
if count == 3 {
b = append(b, en.group[0])
count = 1
} else {
count++
}
}
b = append(b, s[i])
}
for j := len(symbol) - 1; j >= 0; j-- {
b = append(b, symbol[j])
}
if num < 0 {
b = append(b, en.minus[0])
}
// reverse
for i, j := 0, len(b)-1; i < j; i, j = i+1, j-1 {
b[i], b[j] = b[j], b[i]
}
if int(v) < 2 {
if v == 0 {
b = append(b, en.decimal...)
}
for i := 0; i < 2-int(v); i++ {
b = append(b, '0')
}
}
return string(b)
}
// FmtAccounting returns the currency representation of 'num' with digits/precision of 'v' for 'en'
// in accounting notation.
func (en *en) FmtAccounting(num float64, v uint64, currency currency.Type) string {
s := strconv.FormatFloat(math.Abs(num), 'f', int(v), 64)
symbol := en.currencies[currency]
l := len(s) + len(symbol) + 4 + 1*len(s[:len(s)-int(v)-1])/3
count := 0
inWhole := v == 0
b := make([]byte, 0, l)
for i := len(s) - 1; i >= 0; i-- {
if s[i] == '.' {
b = append(b, en.decimal[0])
inWhole = true
continue
}
if inWhole {
if count == 3 {
b = append(b, en.group[0])
count = 1
} else {
count++
}
}
b = append(b, s[i])
}
if num < 0 {
for j := len(symbol) - 1; j >= 0; j-- {
b = append(b, symbol[j])
}
b = append(b, en.currencyNegativePrefix[0])
} else {
for j := len(symbol) - 1; j >= 0; j-- {
b = append(b, symbol[j])
}
}
// reverse
for i, j := 0, len(b)-1; i < j; i, j = i+1, j-1 {
b[i], b[j] = b[j], b[i]
}
if int(v) < 2 {
if v == 0 {
b = append(b, en.decimal...)
}
for i := 0; i < 2-int(v); i++ {
b = append(b, '0')
}
}
if num < 0 {
b = append(b, en.currencyNegativeSuffix...)
}
return string(b)
}
// FmtDateShort returns the short date representation of 't' for 'en'
func (en *en) FmtDateShort(t time.Time) string {
b := make([]byte, 0, 32)
b = strconv.AppendInt(b, int64(t.Month()), 10)
b = append(b, []byte{0x2f}...)
b = strconv.AppendInt(b, int64(t.Day()), 10)
b = append(b, []byte{0x2f}...)
if t.Year() > 9 {
b = append(b, strconv.Itoa(t.Year())[2:]...)
} else {
b = append(b, strconv.Itoa(t.Year())[1:]...)
}
return string(b)
}
// FmtDateMedium returns the medium date representation of 't' for 'en'
func (en *en) FmtDateMedium(t time.Time) string {
b := make([]byte, 0, 32)
b = append(b, en.monthsAbbreviated[t.Month()]...)
b = append(b, []byte{0x20}...)
b = strconv.AppendInt(b, int64(t.Day()), 10)
b = append(b, []byte{0x2c, 0x20}...)
if t.Year() > 0 {
b = strconv.AppendInt(b, int64(t.Year()), 10)
} else {
b = strconv.AppendInt(b, int64(-t.Year()), 10)
}
return string(b)
}
// FmtDateLong returns the long date representation of 't' for 'en'
func (en *en) FmtDateLong(t time.Time) string {
b := make([]byte, 0, 32)
b = append(b, en.monthsWide[t.Month()]...)
b = append(b, []byte{0x20}...)
b = strconv.AppendInt(b, int64(t.Day()), 10)
b = append(b, []byte{0x2c, 0x20}...)
if t.Year() > 0 {
b = strconv.AppendInt(b, int64(t.Year()), 10)
} else {
b = strconv.AppendInt(b, int64(-t.Year()), 10)
}
return string(b)
}
// FmtDateFull returns the full date representation of 't' for 'en'
func (en *en) FmtDateFull(t time.Time) string {
b := make([]byte, 0, 32)
b = append(b, en.daysWide[t.Weekday()]...)
b = append(b, []byte{0x2c, 0x20}...)
b = append(b, en.monthsWide[t.Month()]...)
b = append(b, []byte{0x20}...)
b = strconv.AppendInt(b, int64(t.Day()), 10)
b = append(b, []byte{0x2c, 0x20}...)
if t.Year() > 0 {
b = strconv.AppendInt(b, int64(t.Year()), 10)
} else {
b = strconv.AppendInt(b, int64(-t.Year()), 10)
}
return string(b)
}
// FmtTimeShort returns the short time representation of 't' for 'en'
func (en *en) FmtTimeShort(t time.Time) string {
b := make([]byte, 0, 32)
h := t.Hour()
if h > 12 {
h -= 12
}
b = strconv.AppendInt(b, int64(h), 10)
b = append(b, en.timeSeparator...)
if t.Minute() < 10 {
b = append(b, '0')
}
b = strconv.AppendInt(b, int64(t.Minute()), 10)
b = append(b, []byte{0x20}...)
if t.Hour() < 12 {
b = append(b, en.periodsAbbreviated[0]...)
} else {
b = append(b, en.periodsAbbreviated[1]...)
}
return string(b)
}
// FmtTimeMedium returns the medium time representation of 't' for 'en'
func (en *en) FmtTimeMedium(t time.Time) string {
b := make([]byte, 0, 32)
h := t.Hour()
if h > 12 {
h -= 12
}
b = strconv.AppendInt(b, int64(h), 10)
b = append(b, en.timeSeparator...)
if t.Minute() < 10 {
b = append(b, '0')
}
b = strconv.AppendInt(b, int64(t.Minute()), 10)
b = append(b, en.timeSeparator...)
if t.Second() < 10 {
b = append(b, '0')
}
b = strconv.AppendInt(b, int64(t.Second()), 10)
b = append(b, []byte{0x20}...)
if t.Hour() < 12 {
b = append(b, en.periodsAbbreviated[0]...)
} else {
b = append(b, en.periodsAbbreviated[1]...)
}
return string(b)
}
// FmtTimeLong returns the long time representation of 't' for 'en'
func (en *en) FmtTimeLong(t time.Time) string {
b := make([]byte, 0, 32)
h := t.Hour()
if h > 12 {
h -= 12
}
b = strconv.AppendInt(b, int64(h), 10)
b = append(b, en.timeSeparator...)
if t.Minute() < 10 {
b = append(b, '0')
}
b = strconv.AppendInt(b, int64(t.Minute()), 10)
b = append(b, en.timeSeparator...)
if t.Second() < 10 {
b = append(b, '0')
}
b = strconv.AppendInt(b, int64(t.Second()), 10)
b = append(b, []byte{0x20}...)
if t.Hour() < 12 {
b = append(b, en.periodsAbbreviated[0]...)
} else {
b = append(b, en.periodsAbbreviated[1]...)
}
b = append(b, []byte{0x20}...)
tz, _ := t.Zone()
b = append(b, tz...)
return string(b)
}
// FmtTimeFull returns the full time representation of 't' for 'en'
func (en *en) FmtTimeFull(t time.Time) string {
b := make([]byte, 0, 32)
h := t.Hour()
if h > 12 {
h -= 12
}
b = strconv.AppendInt(b, int64(h), 10)
b = append(b, en.timeSeparator...)
if t.Minute() < 10 {
b = append(b, '0')
}
b = strconv.AppendInt(b, int64(t.Minute()), 10)
b = append(b, en.timeSeparator...)
if t.Second() < 10 {
b = append(b, '0')
}
b = strconv.AppendInt(b, int64(t.Second()), 10)
b = append(b, []byte{0x20}...)
if t.Hour() < 12 {
b = append(b, en.periodsAbbreviated[0]...)
} else {
b = append(b, en.periodsAbbreviated[1]...)
}
b = append(b, []byte{0x20}...)
tz, _ := t.Zone()
if btz, ok := en.timezones[tz]; ok {
b = append(b, btz...)
} else {
b = append(b, tz...)
}
return string(b)
}
Binary file not shown.

After

Width:  |  Height:  |  Size: 36 KiB

+293
View File
@@ -0,0 +1,293 @@
package locales
import (
"strconv"
"time"
"github.com/go-playground/locales/currency"
)
// // ErrBadNumberValue is returned when the number passed for
// // plural rule determination cannot be parsed
// type ErrBadNumberValue struct {
// NumberValue string
// InnerError error
// }
// // Error returns ErrBadNumberValue error string
// func (e *ErrBadNumberValue) Error() string {
// return fmt.Sprintf("Invalid Number Value '%s' %s", e.NumberValue, e.InnerError)
// }
// var _ error = new(ErrBadNumberValue)
// PluralRule denotes the type of plural rules
type PluralRule int
// PluralRule's
const (
PluralRuleUnknown PluralRule = iota
PluralRuleZero // zero
PluralRuleOne // one - singular
PluralRuleTwo // two - dual
PluralRuleFew // few - paucal
PluralRuleMany // many - also used for fractions if they have a separate class
PluralRuleOther // other - required—general plural form—also used if the language only has a single form
)
const (
pluralsString = "UnknownZeroOneTwoFewManyOther"
)
// Translator encapsulates an instance of a locale
// NOTE: some values are returned as a []byte just in case the caller
// wishes to add more and can help avoid allocations; otherwise just cast as string
type Translator interface {
// The following Functions are for overriding, debugging or developing
// with a Translator Locale
// Locale returns the string value of the translator
Locale() string
// returns an array of cardinal plural rules associated
// with this translator
PluralsCardinal() []PluralRule
// returns an array of ordinal plural rules associated
// with this translator
PluralsOrdinal() []PluralRule
// returns an array of range plural rules associated
// with this translator
PluralsRange() []PluralRule
// returns the cardinal PluralRule given 'num' and digits/precision of 'v' for locale
CardinalPluralRule(num float64, v uint64) PluralRule
// returns the ordinal PluralRule given 'num' and digits/precision of 'v' for locale
OrdinalPluralRule(num float64, v uint64) PluralRule
// returns the ordinal PluralRule given 'num1', 'num2' and digits/precision of 'v1' and 'v2' for locale
RangePluralRule(num1 float64, v1 uint64, num2 float64, v2 uint64) PluralRule
// returns the locales abbreviated month given the 'month' provided
MonthAbbreviated(month time.Month) string
// returns the locales abbreviated months
MonthsAbbreviated() []string
// returns the locales narrow month given the 'month' provided
MonthNarrow(month time.Month) string
// returns the locales narrow months
MonthsNarrow() []string
// returns the locales wide month given the 'month' provided
MonthWide(month time.Month) string
// returns the locales wide months
MonthsWide() []string
// returns the locales abbreviated weekday given the 'weekday' provided
WeekdayAbbreviated(weekday time.Weekday) string
// returns the locales abbreviated weekdays
WeekdaysAbbreviated() []string
// returns the locales narrow weekday given the 'weekday' provided
WeekdayNarrow(weekday time.Weekday) string
// WeekdaysNarrowreturns the locales narrow weekdays
WeekdaysNarrow() []string
// returns the locales short weekday given the 'weekday' provided
WeekdayShort(weekday time.Weekday) string
// returns the locales short weekdays
WeekdaysShort() []string
// returns the locales wide weekday given the 'weekday' provided
WeekdayWide(weekday time.Weekday) string
// returns the locales wide weekdays
WeekdaysWide() []string
// The following Functions are common Formatting functionsfor the Translator's Locale
// returns 'num' with digits/precision of 'v' for locale and handles both Whole and Real numbers based on 'v'
FmtNumber(num float64, v uint64) string
// returns 'num' with digits/precision of 'v' for locale and handles both Whole and Real numbers based on 'v'
// NOTE: 'num' passed into FmtPercent is assumed to be in percent already
FmtPercent(num float64, v uint64) string
// returns the currency representation of 'num' with digits/precision of 'v' for locale
FmtCurrency(num float64, v uint64, currency currency.Type) string
// returns the currency representation of 'num' with digits/precision of 'v' for locale
// in accounting notation.
FmtAccounting(num float64, v uint64, currency currency.Type) string
// returns the short date representation of 't' for locale
FmtDateShort(t time.Time) string
// returns the medium date representation of 't' for locale
FmtDateMedium(t time.Time) string
// returns the long date representation of 't' for locale
FmtDateLong(t time.Time) string
// returns the full date representation of 't' for locale
FmtDateFull(t time.Time) string
// returns the short time representation of 't' for locale
FmtTimeShort(t time.Time) string
// returns the medium time representation of 't' for locale
FmtTimeMedium(t time.Time) string
// returns the long time representation of 't' for locale
FmtTimeLong(t time.Time) string
// returns the full time representation of 't' for locale
FmtTimeFull(t time.Time) string
}
// String returns the string value of PluralRule
func (p PluralRule) String() string {
switch p {
case PluralRuleZero:
return pluralsString[7:11]
case PluralRuleOne:
return pluralsString[11:14]
case PluralRuleTwo:
return pluralsString[14:17]
case PluralRuleFew:
return pluralsString[17:20]
case PluralRuleMany:
return pluralsString[20:24]
case PluralRuleOther:
return pluralsString[24:]
default:
return pluralsString[:7]
}
}
//
// Precision Notes:
//
// must specify a precision >= 0, and here is why https://play.golang.org/p/LyL90U0Vyh
//
// v := float64(3.141)
// i := float64(int64(v))
//
// fmt.Println(v - i)
//
// or
//
// s := strconv.FormatFloat(v-i, 'f', -1, 64)
// fmt.Println(s)
//
// these will not print what you'd expect: 0.14100000000000001
// and so this library requires a precision to be specified, or
// inaccurate plural rules could be applied.
//
//
//
// n - absolute value of the source number (integer and decimals).
// i - integer digits of n.
// v - number of visible fraction digits in n, with trailing zeros.
// w - number of visible fraction digits in n, without trailing zeros.
// f - visible fractional digits in n, with trailing zeros.
// t - visible fractional digits in n, without trailing zeros.
//
//
// Func(num float64, v uint64) // v = digits/precision and prevents -1 as a special case as this can lead to very unexpected behaviour, see precision note's above.
//
// n := math.Abs(num)
// i := int64(n)
// v := v
//
//
// w := strconv.FormatFloat(num-float64(i), 'f', int(v), 64) // then parse backwards on string until no more zero's....
// f := strconv.FormatFloat(n, 'f', int(v), 64) // then turn everything after decimal into an int64
// t := strconv.FormatFloat(n, 'f', int(v), 64) // then parse backwards on string until no more zero's....
//
//
//
// General Inclusion Rules
// - v will always be available inherently
// - all require n
// - w requires i
//
// W returns the number of visible fraction digits in N, without trailing zeros.
func W(n float64, v uint64) (w int64) {
s := strconv.FormatFloat(n-float64(int64(n)), 'f', int(v), 64)
// with either be '0' or '0.xxxx', so if 1 then w will be zero
// otherwise need to parse
if len(s) != 1 {
s = s[2:]
end := len(s) + 1
for i := end; i >= 0; i-- {
if s[i] != '0' {
end = i + 1
break
}
}
w = int64(len(s[:end]))
}
return
}
// F returns the visible fractional digits in N, with trailing zeros.
func F(n float64, v uint64) (f int64) {
s := strconv.FormatFloat(n-float64(int64(n)), 'f', int(v), 64)
// with either be '0' or '0.xxxx', so if 1 then f will be zero
// otherwise need to parse
if len(s) != 1 {
// ignoring error, because it can't fail as we generated
// the string internally from a real number
f, _ = strconv.ParseInt(s[2:], 10, 64)
}
return
}
// T returns the visible fractional digits in N, without trailing zeros.
func T(n float64, v uint64) (t int64) {
s := strconv.FormatFloat(n-float64(int64(n)), 'f', int(v), 64)
// with either be '0' or '0.xxxx', so if 1 then t will be zero
// otherwise need to parse
if len(s) != 1 {
s = s[2:]
end := len(s) + 1
for i := end; i >= 0; i-- {
if s[i] != '0' {
end = i + 1
break
}
}
// ignoring error, because it can't fail as we generated
// the string internally from a real number
t, _ = strconv.ParseInt(s[:end], 10, 64)
}
return
}