+
{
insertMarkdown(
markdown,
textareaRef.current,
- (text, caretPos) => {
- onChange(text)
- textareaRef.current.focus()
- textareaRef.current.selectionEnd = caretPos
- }
+ insertMarkdownCallback
)
if (markdown === MENTION) {
@@ -231,20 +262,18 @@ export const RichTextEditor = forwardRef(
/>
{previewMode ? (
) : (
-
+
-
+ {errorText && (
+ {errorText}
+ )}
+ {helpText && {helpText}}
+
)}
@@ -265,13 +301,20 @@ export const RichTextEditor = forwardRef(
}
)
-RichTextEditor.displayName = 'RichTextEditor'
+Editor.displayName = 'Editor'
+
+Editor.defaultProps = {
+ initialFocus: true,
+ resizable: true,
+}
-RichTextEditor.propTypes = {
+Editor.propTypes = {
value: PropTypes.string.isRequired,
onChange: PropTypes.func.isRequired,
disabled: PropTypes.bool,
errorText: PropTypes.string,
helpText: PropTypes.string,
+ initialFocus: PropTypes.bool,
inputPlaceholder: PropTypes.string,
+ resizable: PropTypes.bool,
}
diff --git a/src/components/RichText/Editor/__tests__/Editor.spec.js b/src/components/RichText/Editor/__tests__/Editor.spec.js
new file mode 100644
index 000000000..97eaf217b
--- /dev/null
+++ b/src/components/RichText/Editor/__tests__/Editor.spec.js
@@ -0,0 +1,47 @@
+import '@testing-library/jest-dom'
+import { render, screen, fireEvent } from '@testing-library/react'
+import React from 'react'
+import { Editor } from '../Editor.js'
+
+const mockConvertCtrlKey = jest.fn()
+jest.mock('../markdownHandler.js', () => ({
+ convertCtrlKey: () => mockConvertCtrlKey(),
+}))
+
+jest.mock('../../../UserMention/UserMentionWrapper.js', () => ({
+ UserMentionWrapper: jest.fn((props) => <>{props.children}>),
+}))
+
+describe('RichText: Editor component', () => {
+ const componentProps = {
+ value: '',
+ onChange: jest.fn(),
+ }
+
+ beforeEach(() => {
+ mockConvertCtrlKey.mockClear()
+ })
+
+ const renderComponent = (props) => {
+ return render(
)
+ }
+
+ it('renders a result', () => {
+ renderComponent(componentProps)
+
+ expect(
+ screen.getByTestId('@dhis2-analytics-richtexteditor')
+ ).toBeVisible()
+ })
+
+ it('calls convertCtrlKey on keydown', () => {
+ renderComponent(componentProps)
+
+ fireEvent.keyDown(screen.getByRole('textbox'), {
+ key: 'A',
+ code: 'keyA',
+ })
+
+ expect(mockConvertCtrlKey).toHaveBeenCalled()
+ })
+})
diff --git a/src/components/RichText/Editor/__tests__/convertCtrlKey.spec.js b/src/components/RichText/Editor/__tests__/convertCtrlKey.spec.js
new file mode 100644
index 000000000..5ebc93a2b
--- /dev/null
+++ b/src/components/RichText/Editor/__tests__/convertCtrlKey.spec.js
@@ -0,0 +1,230 @@
+import { convertCtrlKey } from '../markdownHandler.js'
+
+describe('convertCtrlKey', () => {
+ it('does not trigger callback if no ctrl key', () => {
+ const cb = jest.fn()
+ const e = { key: 'j', preventDefault: () => {} }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).not.toHaveBeenCalled()
+ })
+
+ describe('when ctrl key + "b" pressed', () => {
+ it('triggers callback with open/close markers and caret pos in between', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ ctrlKey: true,
+ target: {
+ selectionStart: 0,
+ selectionEnd: 0,
+ value: 'rainbow dash',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('** rainbow dash', 1)
+ })
+
+ it('triggers callback with open/close markers and caret pos in between (end of text)', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ ctrlKey: true,
+ target: {
+ selectionStart: 22,
+ selectionEnd: 22,
+ value: 'rainbow dash is purple',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('rainbow dash is purple **', 24)
+ })
+
+ it('triggers callback with open/close markers mid-text with surrounding spaces (1)', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ metaKey: true,
+ target: {
+ selectionStart: 4, // caret located just before "quick"
+ selectionEnd: 4,
+ value: 'the quick brown fox',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('the ** quick brown fox', 5)
+ })
+
+ it('triggers callback with open/close markers mid-text with surrounding spaces (2)', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ metaKey: true,
+ target: {
+ selectionStart: 3, // caret located just after "the"
+ selectionEnd: 3,
+ value: 'the quick brown fox',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('the ** quick brown fox', 5)
+ })
+
+ it('triggers callback with correct double markers and padding', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ metaKey: true,
+ target: {
+ selectionStart: 9, // between the underscores
+ selectionEnd: 9,
+ value: 'rainbow __',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('rainbow _**_', 10)
+ })
+
+ describe('selected text', () => {
+ it('triggers callback with open/close markers around text and caret pos after closing marker', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ metaKey: true,
+ target: {
+ selectionStart: 5, // "ow da" is selected
+ selectionEnd: 10,
+ value: 'rainbow dash is purple',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith(
+ 'rainb *ow da* sh is purple',
+ 13
+ )
+ })
+
+ it('triggers callback with open/close markers around text when starting at beginning of line', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ metaKey: true,
+ target: {
+ selectionStart: 0, // "rainbow" is selected
+ selectionEnd: 7,
+ value: 'rainbow dash is purple',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('*rainbow* dash is purple', 9)
+ })
+
+ it('triggers callback with open/close markers around text when ending at end of line', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ metaKey: true,
+ target: {
+ selectionStart: 16, // "purple" is selected
+ selectionEnd: 22,
+ value: 'rainbow dash is purple',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('rainbow dash is *purple*', 24)
+ })
+
+ it('triggers callback with open/close markers around word', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ metaKey: true,
+ target: {
+ selectionStart: 8, // "dash" is selected
+ selectionEnd: 12,
+ value: 'rainbow dash is purple',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('rainbow *dash* is purple', 14)
+ })
+
+ it('triggers callback with leading/trailing spaces trimmed from selection', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'b',
+ metaKey: true,
+ target: {
+ selectionStart: 8, // " dash " is selected (note leading and trailing space)
+ selectionEnd: 13,
+ value: 'rainbow dash is purple',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('rainbow *dash* is purple', 14)
+ })
+ })
+ })
+
+ describe('when ctrl key + "i" pressed', () => {
+ it('triggers callback with open/close italics markers and caret pos in between', () => {
+ const cb = jest.fn()
+ const e = {
+ key: 'i',
+ ctrlKey: true,
+ target: {
+ selectionStart: 0,
+ selectionEnd: 0,
+ value: '',
+ },
+ preventDefault: () => {},
+ }
+
+ convertCtrlKey(e, cb)
+
+ expect(cb).toHaveBeenCalled()
+ expect(cb).toHaveBeenCalledWith('__', 1)
+ })
+ })
+})
diff --git a/src/components/Interpretations/common/RichTextEditor/markdownHandler.js b/src/components/RichText/Editor/markdownHandler.js
similarity index 86%
rename from src/components/Interpretations/common/RichTextEditor/markdownHandler.js
rename to src/components/RichText/Editor/markdownHandler.js
index e32a771a5..f9b01895f 100644
--- a/src/components/Interpretations/common/RichTextEditor/markdownHandler.js
+++ b/src/components/RichText/Editor/markdownHandler.js
@@ -89,14 +89,20 @@ export const insertMarkdown = (markdown, target, cb) => {
if (start === end) {
//no text
const valueArr = value.split('')
- let markdown = marker.prefix
+ let markdownString = marker.prefix
if (marker.postfix) {
- markdown += marker.postfix
+ markdownString += marker.postfix
}
- valueArr.splice(start, 0, padMarkers(markdown))
+ valueArr.splice(start, 0, padMarkers(markdownString))
newValue = valueArr.join('')
+
+ // for smileys, put the caret after a space
+ if (Object.keys(emojis).includes(markdown)) {
+ newValue += ' '
+ caretPos = caretPos + newValue.length - 1
+ }
} else {
const text = value.slice(start, end)
const trimmedText = trim(text) // TODO really needed?
@@ -104,15 +110,15 @@ export const insertMarkdown = (markdown, target, cb) => {
// adjust caretPos based on trimmed text selection
caretPos = caretPos - (text.length - trimmedText.length) + 1
- let markdown = `${marker.prefix}${trimmedText}`
+ let markdownString = `${marker.prefix}${trimmedText}`
if (marker.postfix) {
- markdown += marker.postfix
+ markdownString += marker.postfix
}
newValue = [
value.slice(0, start),
- padMarkers(markdown),
+ padMarkers(markdownString),
value.slice(end),
].join('')
}
diff --git a/src/components/Interpretations/common/RichTextEditor/styles/RichTextEditor.style.js b/src/components/RichText/Editor/styles/Editor.style.js
similarity index 81%
rename from src/components/Interpretations/common/RichTextEditor/styles/RichTextEditor.style.js
rename to src/components/RichText/Editor/styles/Editor.style.js
index 53b9a5457..607be4c8d 100644
--- a/src/components/Interpretations/common/RichTextEditor/styles/RichTextEditor.style.js
+++ b/src/components/RichText/Editor/styles/Editor.style.js
@@ -6,18 +6,29 @@ export const mainClasses = css`
display: flex;
flex-direction: column;
width: 100%;
+ height: 100%;
}
.preview {
+ padding: ${spacers.dp8} ${spacers.dp12};
font-size: 14px;
- line-height: 19px;
+ line-height: ${spacers.dp16};
color: ${colors.grey900};
+ overflow-y: auto;
+ scroll-behavior: smooth;
+ }
+
+ .edit {
+ width: 100%;
+ height: 100%;
+ scroll-behavior: smooth;
}
.textarea {
width: 100%;
+ height: 100%;
box-sizing: border-box;
- padding: ${spacers.dp8} ${spacers.dp12};
+ padding: ${spacers.dp8} 15px;
color: ${colors.grey900};
background-color: ${colors.white};
@@ -31,12 +42,20 @@ export const mainClasses = css`
font-size: 14px;
line-height: ${spacers.dp16};
user-select: text;
+ resize: none;
+ }
+
+ .textarea.resizable {
+ resize: vertical;
}
.textarea:focus {
outline: none;
box-shadow: 0 0 0 3px ${theme.focus};
- width: calc(100% - 3px);
+ width: calc(100% - 6px);
+ height: calc(100% - 3px);
+ padding: ${spacers.dp8} ${spacers.dp12};
+ margin-left: 3px;
}
.textarea:disabled {
diff --git a/src/components/RichText/Parser/MdParser.js b/src/components/RichText/Parser/MdParser.js
new file mode 100644
index 000000000..0ec97a5f6
--- /dev/null
+++ b/src/components/RichText/Parser/MdParser.js
@@ -0,0 +1,125 @@
+import MarkdownIt from 'markdown-it'
+
+const emojiDb = {
+ ':-)': '\u{1F642}',
+ ':)': '\u{1F642}',
+ ':-(': '\u{1F641}',
+ ':(': '\u{1F641}',
+ ':+1': '\u{1F44D}',
+ ':-1': '\u{1F44E}',
+}
+
+const codes = {
+ bold: {
+ name: 'bold',
+ char: '*',
+ domEl: 'strong',
+ encodedChar: 0x2a,
+ // see https://regex101.com/r/evswdV/8 for explanation of regexp
+ regexString: '\\B\\*((?!\\s)[^*]+(?:\\b|[^*\\s]))\\*\\B',
+ contentFn: (val) => val,
+ },
+ italic: {
+ name: 'italic',
+ char: '_',
+ domEl: 'em',
+ encodedChar: 0x5f,
+ // see https://regex101.com/r/p6LpjK/6 for explanation of regexp
+ regexString: '\\b_((?!\\s)[^_]+(?:\\B|[^_\\s]))_\\b',
+ contentFn: (val) => val,
+ },
+ emoji: {
+ name: 'emoji',
+ char: ':',
+ domEl: 'span',
+ encodedChar: 0x3a,
+ regexString: '^(:-\\)|:\\)|:\\(|:-\\(|:\\+1|:-1)',
+ contentFn: (val) => emojiDb[val],
+ },
+}
+
+let linksInText
+
+const markerIsInLinkText = (pos) =>
+ linksInText.some((link) => pos >= link.index && pos <= link.lastIndex)
+
+const parse = (code) => (state, silent) => {
+ if (silent) {
+ return false
+ }
+
+ const start = state.pos
+
+ // skip parsing emphasis if marker is within a link
+ if (markerIsInLinkText(start)) {
+ return false
+ }
+
+ const marker = state.src.charCodeAt(start)
+
+ // marker character: "_", "*", ":"
+ if (marker !== codes[code].encodedChar) {
+ return false
+ }
+
+ const MARKER_REGEX = new RegExp(codes[code].regexString)
+ const token = state.src.slice(start)
+
+ if (MARKER_REGEX.test(token)) {
+ const markerMatch = token.match(MARKER_REGEX)
+
+ // skip parsing sections where the marker is not at the start of the token
+ if (markerMatch.index !== 0) {
+ return false
+ }
+
+ const text = markerMatch[1]
+
+ state.push(`${codes[code].domEl}_open`, codes[code].domEl, 1)
+
+ const t = state.push('text', '', 0)
+ t.content = codes[code].contentFn(text)
+
+ state.push(`${codes.bold.domEl}_close`, codes[code].domEl, -1)
+ state.pos += markerMatch[0].length
+
+ return true
+ }
+
+ return false
+}
+
+export class MdParser {
+ constructor() {
+ // disable all rules, enable autolink for URLs and email addresses
+ const md = new MarkdownIt('zero', { linkify: true, breaks: true })
+
+ // *bold* ->
bold
+ md.inline.ruler.push('strong', parse(codes.bold.name))
+
+ // _italic_ ->
italic
+ md.inline.ruler.push('italic', parse(codes.italic.name))
+
+ // :-) :) :-( :( :+1 :-1 ->
[unicode]
+ md.inline.ruler.push('emoji', parse(codes.emoji.name))
+
+ md.enable([
+ 'heading',
+ 'link',
+ 'linkify',
+ 'list',
+ 'newline',
+ 'strong',
+ 'italic',
+ 'emoji',
+ ])
+
+ this.md = md
+ }
+
+ render(text) {
+ linksInText = this.md.linkify.match(text) || []
+
+ return this.md.render(text)
+ }
+}
diff --git a/src/components/RichText/Parser/Parser.js b/src/components/RichText/Parser/Parser.js
new file mode 100644
index 000000000..172049bc1
--- /dev/null
+++ b/src/components/RichText/Parser/Parser.js
@@ -0,0 +1,28 @@
+import PropTypes from 'prop-types'
+import React, { useMemo } from 'react'
+import { MdParser } from './MdParser.js'
+
+export const Parser = ({ children, style }) => {
+ const MdParserInstance = useMemo(() => new MdParser(), [])
+
+ return children ? (
+
+ ) : null
+}
+
+Parser.defaultProps = {
+ style: null,
+}
+
+Parser.propTypes = {
+ children: PropTypes.oneOfType([
+ PropTypes.arrayOf(PropTypes.node),
+ PropTypes.node,
+ ]),
+ style: PropTypes.object,
+}
diff --git a/src/components/RichText/Parser/__tests__/MdParser.spec.js b/src/components/RichText/Parser/__tests__/MdParser.spec.js
new file mode 100644
index 000000000..397b27e76
--- /dev/null
+++ b/src/components/RichText/Parser/__tests__/MdParser.spec.js
@@ -0,0 +1,166 @@
+import { MdParser } from '../MdParser.js'
+
+const Parser = new MdParser()
+
+describe('MdParser class', () => {
+ it('converts text into HTML', () => {
+ const inlineTests = [
+ ['_italic_', '
italic'],
+ ['*bold*', '
bold'],
+ [
+ '_ not italic because there is a space _',
+ '_ not italic because there is a space _',
+ ],
+ [':-)', '
\u{1F642}'],
+ [':)', '
\u{1F642}'],
+ [':-(', '
\u{1F641}'],
+ [':(', '
\u{1F641}'],
+ [':+1', '
\u{1F44D}'],
+ [':-1', '
\u{1F44E}'],
+ [
+ 'mixed _italic_ *bold* and :+1',
+ 'mixed
italic bold and
\u{1F44D}',
+ ],
+ ['_italic with * inside_', '
italic with * inside'],
+ ['*bold with _ inside*', '
bold with _ inside'],
+
+ // italic marker followed by : should work
+ ['_italic_:', '
italic:'],
+ [
+ '_italic_: some text, *bold*: some other text',
+ '
italic: some text,
bold: some other text',
+ ],
+ // bold marker followed by : should work
+ ['*bold*:', '
bold:'],
+ [
+ '*bold*: some text, _italic_: some other text',
+ '
bold: some text,
italic: some other text',
+ ],
+
+ // italic marker inside an italic string not allowed
+ ['_italic with _ inside_', '_italic with _ inside_'],
+ // bold marker inside a bold string not allowed
+ ['*bold with * inside*', '*bold with * inside*'],
+ [
+ '_multiple_ italic in the _same line_',
+ '
multiple italic in the
same line',
+ ],
+ // nested italic/bold combinations not allowed
+ [
+ '_italic with *bold* inside_',
+ '
italic with *bold* inside',
+ ],
+ [
+ '*bold with _italic_ inside*',
+ '
bold with _italic_ inside',
+ ],
+ ['text with : and :)', 'text with : and
\u{1F642}'],
+ [
+ '(parenthesis and :))',
+ '(parenthesis and
\u{1F642})',
+ ],
+ [
+ ':((parenthesis:))',
+ '
\u{1F641}(parenthesis
\u{1F642})',
+ ],
+ [':+1+1', '
\u{1F44D}+1'],
+ ['-1:-1', '-1
\u{1F44E}'],
+
+ // links
+ [
+ 'example.com/path',
+ '
example.com/path',
+ ],
+
+ // not recognized links with italic marker inside not converted
+ [
+ 'example_with_underscore.com/path',
+ 'example_with_underscore.com/path',
+ ],
+ [
+ 'example_with_underscore.com/path_with_underscore',
+ 'example_with_underscore.com/path_with_underscore',
+ ],
+
+ // markers around non-recognized links
+ [
+ 'link example_with_underscore.com/path should _not_ be converted',
+ 'link example_with_underscore.com/path should
not be converted',
+ ],
+ [
+ 'link example_with_underscore.com/path should *not* be converted',
+ 'link example_with_underscore.com/path should
not be converted',
+ ],
+
+ // italic marker inside links not converted
+ [
+ 'example.com/path_with_underscore',
+ '
example.com/path_with_underscore',
+ ],
+ [
+ '_italic_ and *bold* with a example.com/link_with_underscore',
+ '
italic and
bold with a
example.com/link_with_underscore',
+ ],
+ [
+ 'example.com/path with *bold* after :)',
+ '
example.com/path with
bold after
\u{1F642}',
+ ],
+ [
+ '_before_ example.com/path_with_underscore *after* :)',
+ '
before example.com/path_with_underscore after \u{1F642}',
+ ],
+
+ // italic/bold markers right after non-word characters
+ [
+ '_If % of ART retention rate after 12 months >90(%)_: Sustain the efforts.',
+ '
If % of ART retention rate after 12 months >90(%): Sustain the efforts.',
+ ],
+ [
+ '*If % of ART retention rate after 12 months >90(%)*: Sustain the efforts.',
+ '
If % of ART retention rate after 12 months >90(%): Sustain the efforts.',
+ ],
+ ]
+
+ inlineTests.forEach((test) => {
+ const renderedText = Parser.render(test[0])
+
+ expect(renderedText).toEqual(`
${test[1]}
\n`)
+ })
+
+ const blockTests = [
+ // heading
+ ['# Heading 1', '
Heading 1
'],
+ ['## Heading 2', '
Heading 2
'],
+ ['### Heading 3', '
Heading 3
'],
+ ['#### Heading 4', '
Heading 4
'],
+ ['##### Heading 5', '
Heading 5
'],
+ ['###### Heading 6', '
Heading 6
'],
+ ['# *Bold head*', '
Bold head
'],
+ ['## _Italic title_', '
Italic title
'],
+ [
+ '### *Bold* and _italic_ title',
+ '
Bold and italic title
',
+ ],
+
+ // lists
+ [
+ '* first\n* second\n* third',
+ '
',
+ ],
+ [
+ '1. one\n1. two\n1. three\n',
+ '
\n- one
\n- two
\n- three
\n
',
+ ],
+ [
+ '* *first*\n* second\n* _third_',
+ '
',
+ ],
+ ]
+
+ blockTests.forEach((test) => {
+ const renderedText = Parser.render(test[0])
+
+ expect(renderedText).toEqual(`${test[1]}\n`)
+ })
+ })
+})
diff --git a/src/components/RichText/Parser/__tests__/Parser.spec.js b/src/components/RichText/Parser/__tests__/Parser.spec.js
new file mode 100644
index 000000000..26011d492
--- /dev/null
+++ b/src/components/RichText/Parser/__tests__/Parser.spec.js
@@ -0,0 +1,43 @@
+import { shallow } from 'enzyme'
+import React from 'react'
+import { Parser } from '../Parser.js'
+
+jest.mock('../MdParser.js', () => ({
+ MdParser: jest.fn().mockImplementation(() => {
+ return { render: () => 'converted text' }
+ }),
+}))
+
+describe('RichText: Parser component', () => {
+ let richTextParser
+ const defaultProps = {
+ style: { color: 'blue', whiteSpace: 'pre-line' },
+ }
+
+ const renderComponent = (props, text) => {
+ return shallow(
{text})
+ }
+
+ it('should have rendered a result', () => {
+ richTextParser = renderComponent({}, 'test')
+
+ expect(richTextParser).toHaveLength(1)
+ })
+
+ it('should have rendered a result with the style prop', () => {
+ richTextParser = renderComponent(defaultProps, 'test prop')
+
+ expect(richTextParser.props().style).toEqual(defaultProps.style)
+ })
+
+ it('should have rendered content', () => {
+ richTextParser = renderComponent({}, 'plain text')
+
+ expect(richTextParser.html()).toEqual('
converted text
')
+ })
+
+ it('should return null if no children is passed', () => {
+ richTextParser = renderComponent({}, undefined)
+ expect(richTextParser.html()).toBe(null)
+ })
+})
diff --git a/src/components/RichText/index.js b/src/components/RichText/index.js
new file mode 100644
index 000000000..6d9ff0e75
--- /dev/null
+++ b/src/components/RichText/index.js
@@ -0,0 +1,3 @@
+export { Editor as RichTextEditor } from './Editor/Editor.js'
+export { Parser as RichTextParser } from './Parser/Parser.js'
+export { MdParser as RichTextMdParser } from './Parser/MdParser.js'
diff --git a/src/components/Interpretations/common/UserMention/UserList.js b/src/components/UserMention/UserList.js
similarity index 100%
rename from src/components/Interpretations/common/UserMention/UserList.js
rename to src/components/UserMention/UserList.js
diff --git a/src/components/Interpretations/common/UserMention/UserMentionWrapper.js b/src/components/UserMention/UserMentionWrapper.js
similarity index 88%
rename from src/components/Interpretations/common/UserMention/UserMentionWrapper.js
rename to src/components/UserMention/UserMentionWrapper.js
index 394cc39bc..4550d5513 100644
--- a/src/components/Interpretations/common/UserMention/UserMentionWrapper.js
+++ b/src/components/UserMention/UserMentionWrapper.js
@@ -2,12 +2,12 @@ import i18n from '@dhis2/d2-i18n'
import {
CenteredContent,
CircularLoader,
+ Layer,
Menu,
MenuSectionHeader,
MenuItem,
Popper,
Card,
- Portal,
} from '@dhis2/ui'
import PropTypes from 'prop-types'
import React, { useState, useRef } from 'react'
@@ -43,6 +43,7 @@ export const UserMentionWrapper = ({
inputReference,
onUserSelect,
}) => {
+ const [listIsOpen, setListIsOpen] = useState(false)
const [captureText, setCaptureText] = useState(false)
const [capturedText, setCapturedText] = useState('')
const [cloneText, setCloneText] = useState('')
@@ -54,6 +55,7 @@ export const UserMentionWrapper = ({
})
const reset = () => {
+ setListIsOpen(false)
setCaptureText(false)
setCapturedText('')
setCloneText('')
@@ -63,6 +65,12 @@ export const UserMentionWrapper = ({
clear()
}
+ // focus the input/textarea when the user list is closed by clicking above the input/textarea
+ const onClick = () => inputReference.current.focus()
+
+ // close the user list when clicking in the input/textarea or outside of it (input/textarea blur)
+ const onUserListClose = () => reset()
+
// event bubbles up from the input/textarea
const onInput = ({ target }) => {
const { selectionEnd, value } = target
@@ -72,10 +80,12 @@ export const UserMentionWrapper = ({
const spacePosition = value.indexOf(' ', captureStartPosition - 1)
- const filterValue = value.substring(
- captureStartPosition,
- spacePosition > 0 ? spacePosition : selectionEnd + 1
- )
+ const filterValue = value
+ .substring(
+ captureStartPosition,
+ spacePosition > 0 ? spacePosition : selectionEnd + 1
+ )
+ .replace(/\n+/, '')
if (filterValue !== capturedText) {
setCapturedText(filterValue)
@@ -91,6 +101,7 @@ export const UserMentionWrapper = ({
const { selectionStart } = target
if (!captureText && key === '@') {
+ setListIsOpen(true)
setCaptureText(true)
setCaptureStartPosition(selectionStart + 1)
setCloneText(target.value.substring(0, selectionStart) + '@')
@@ -159,16 +170,21 @@ export const UserMentionWrapper = ({
)
}
- const onClick = (user) => () => onSelect(user)
+ const onUserClick = (user) => () => onSelect(user)
return (
-
+
{children}
-
{cloneText}
+
{cloneText}
- {captureText && (
-
+ {listIsOpen && (
+
)}
@@ -228,7 +244,7 @@ export const UserMentionWrapper = ({
-
+
)}
{resolvedHeaderStyle.styles}
@@ -245,5 +261,3 @@ UserMentionWrapper.propTypes = {
onUserSelect: PropTypes.func.isRequired,
children: PropTypes.node,
}
-
-export default UserMentionWrapper
diff --git a/src/components/Interpretations/common/UserMention/styles/UserMentionWrapper.style.js b/src/components/UserMention/styles/UserMentionWrapper.style.js
similarity index 88%
rename from src/components/Interpretations/common/UserMention/styles/UserMentionWrapper.style.js
rename to src/components/UserMention/styles/UserMentionWrapper.style.js
index e98517db1..a075ff11d 100644
--- a/src/components/Interpretations/common/UserMention/styles/UserMentionWrapper.style.js
+++ b/src/components/UserMention/styles/UserMentionWrapper.style.js
@@ -8,6 +8,8 @@ import css from 'styled-jsx/css'
*/
export const userMentionWrapperClasses = css`
.wrapper {
+ width: 100%;
+ height: 100%;
position: relative;
}
.clone {
@@ -15,19 +17,20 @@ export const userMentionWrapperClasses = css`
visibility: hidden;
inset: 0;
box-sizing: border-box;
- padding: ${spacers.dp8} ${spacers.dp12};
+ padding: ${spacers.dp8} 15px;
border: 1px solid ${colors.grey500};
font-size: 14px;
line-height: ${spacers.dp16};
z-index: 1;
pointer-events: none;
}
- .clone > pre {
+ .clone > p {
display: inline;
word-wrap: break-word;
overflow-wrap: break-word;
font: inherit;
margin: 0;
+ white-space: break-spaces;
}
.container {
background-color: ${colors.white};
diff --git a/src/components/Interpretations/common/UserMention/useUserSearchResults.js b/src/components/UserMention/useUserSearchResults.js
similarity index 94%
rename from src/components/Interpretations/common/UserMention/useUserSearchResults.js
rename to src/components/UserMention/useUserSearchResults.js
index b9d46b46d..9adfc4613 100644
--- a/src/components/Interpretations/common/UserMention/useUserSearchResults.js
+++ b/src/components/UserMention/useUserSearchResults.js
@@ -32,10 +32,10 @@ export const useUserSearchResults = ({ searchText }) => {
}, [searchText, debouncedRefetch])
useEffect(() => {
- if (data) {
+ if (fetching === false && data) {
setData(data.users)
}
- }, [data])
+ }, [data, fetching])
return {
users,
diff --git a/src/index.js b/src/index.js
index 0fb8fe59b..1202981b5 100644
--- a/src/index.js
+++ b/src/index.js
@@ -47,6 +47,8 @@ export {
useCachedDataQuery,
} from './components/CachedDataQueryProvider.js'
+export * from './components/RichText/index.js'
+
// Api
export { default as Analytics } from './api/analytics/Analytics.js'
diff --git a/yarn.lock b/yarn.lock
index ca4038043..814fd22bd 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -2453,15 +2453,6 @@
i18next "^10.3"
moment "^2.24.0"
-"@dhis2/d2-ui-rich-text@^7.4.1":
- version "7.4.1"
- resolved "https://registry.yarnpkg.com/@dhis2/d2-ui-rich-text/-/d2-ui-rich-text-7.4.1.tgz#8764208c59c6758bf34765b1dbe01762ce435d11"
- integrity sha512-/n5nE0b4EDI/kX0/aN+vFDOswoWT5JQ3lwtHsUxailvnEHMu4/3l27Q38Z+5qhKwl+jYNB9GOFxWoSiymUgBbw==
- dependencies:
- babel-runtime "^6.26.0"
- markdown-it "^8.4.2"
- prop-types "^15.6.2"
-
"@dhis2/multi-calendar-dates@1.0.0":
version "1.0.0"
resolved "https://registry.yarnpkg.com/@dhis2/multi-calendar-dates/-/multi-calendar-dates-1.0.0.tgz#bf7f49aecdffa9781837a5d60d56a094b74ab4df"
@@ -6090,6 +6081,11 @@ argparse@^1.0.7:
dependencies:
sprintf-js "~1.0.2"
+argparse@^2.0.1:
+ version "2.0.1"
+ resolved "https://registry.yarnpkg.com/argparse/-/argparse-2.0.1.tgz#246f50f3ca78a3240f6c997e8a9bd1eac49e4b38"
+ integrity sha512-8+9WqebbFzpX9OR+Wa6O29asIogeRMzcGtAINdpMHHyAg10f05aSFVBbcEqGf/PXw1EjAZ+q2/bEBg3DvurK3Q==
+
aria-query@^4.2.2:
version "4.2.2"
resolved "https://registry.yarnpkg.com/aria-query/-/aria-query-4.2.2.tgz#0d2ca6c9aceb56b8977e9fed6aed7e15bbd2f83b"
@@ -9537,6 +9533,11 @@ entities@^2.0.0:
resolved "https://registry.yarnpkg.com/entities/-/entities-2.2.0.tgz#098dc90ebb83d8dffa089d55256b351d34c4da55"
integrity sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==
+entities@~3.0.1:
+ version "3.0.1"
+ resolved "https://registry.yarnpkg.com/entities/-/entities-3.0.1.tgz#2b887ca62585e96db3903482d336c1006c3001d4"
+ integrity sha512-WiyBqoomrwMdFG1e0kqvASYfnlb0lp8M5o5Fw2OFq1hNZxxcNk8Ik0Xm7LxzBhuidnZB/UtBqVCgUz3kBOP51Q==
+
enzyme-adapter-react-16@^1.15.6:
version "1.15.6"
resolved "https://registry.yarnpkg.com/enzyme-adapter-react-16/-/enzyme-adapter-react-16-1.15.6.tgz#fd677a658d62661ac5afd7f7f541f141f8085901"
@@ -14194,10 +14195,10 @@ lines-and-columns@^1.1.6:
resolved "https://registry.yarnpkg.com/lines-and-columns/-/lines-and-columns-1.2.4.tgz#eca284f75d2965079309dc0ad9255abb2ebc1632"
integrity sha512-7ylylesZQ/PV29jhEDl3Ufjo6ZX7gCqJr5F7PKrqc93v7fzSymt1BpwEU8nAUXs8qzzvqhbjhK5QZg6Mt/HkBg==
-linkify-it@^2.0.0:
- version "2.2.0"
- resolved "https://registry.yarnpkg.com/linkify-it/-/linkify-it-2.2.0.tgz#e3b54697e78bf915c70a38acd78fd09e0058b1cf"
- integrity sha512-GnAl/knGn+i1U/wjBz3akz2stz+HrHLsxMwHQGofCDfPvlf+gDKN58UtfmUquTY4/MXeE2x7k19KQmeoZi94Iw==
+linkify-it@^4.0.1:
+ version "4.0.1"
+ resolved "https://registry.yarnpkg.com/linkify-it/-/linkify-it-4.0.1.tgz#01f1d5e508190d06669982ba31a7d9f56a5751ec"
+ integrity sha512-C7bfi1UZmoj8+PQx22XyeXCuBlokoyWQL5pWSP+EI6nzRylyThouddufc2c1NDIcP9k5agmN9fLpA7VNJfIiqw==
dependencies:
uc.micro "^1.0.1"
@@ -14644,14 +14645,14 @@ markdown-escapes@^1.0.0:
resolved "https://registry.yarnpkg.com/markdown-escapes/-/markdown-escapes-1.0.4.tgz#c95415ef451499d7602b91095f3c8e8975f78535"
integrity sha512-8z4efJYk43E0upd0NbVXwgSTQs6cT3T06etieCMEg7dRbzCbxUCK/GHlX8mhHRDcp+OLlHkPKsvqQTCvsRl2cg==
-markdown-it@^8.4.2:
- version "8.4.2"
- resolved "https://registry.yarnpkg.com/markdown-it/-/markdown-it-8.4.2.tgz#386f98998dc15a37722aa7722084f4020bdd9b54"
- integrity sha512-GcRz3AWTqSUphY3vsUqQSFMbgR38a4Lh3GWlHRh/7MRwz8mcu9n2IO7HOh+bXHrR9kOPDl5RNCaEsrneb+xhHQ==
+markdown-it@^13.0.1:
+ version "13.0.1"
+ resolved "https://registry.yarnpkg.com/markdown-it/-/markdown-it-13.0.1.tgz#c6ecc431cacf1a5da531423fc6a42807814af430"
+ integrity sha512-lTlxriVoy2criHP0JKRhO2VDG9c2ypWCsT237eDiLqi09rmbKoUetyGHq2uOIRoRS//kfoJckS0eUzzkDR+k2Q==
dependencies:
- argparse "^1.0.7"
- entities "~1.1.1"
- linkify-it "^2.0.0"
+ argparse "^2.0.1"
+ entities "~3.0.1"
+ linkify-it "^4.0.1"
mdurl "^1.0.1"
uc.micro "^1.0.5"
@@ -14736,7 +14737,7 @@ mdn-data@2.0.6:
mdurl@^1.0.0, mdurl@^1.0.1:
version "1.0.1"
resolved "https://registry.yarnpkg.com/mdurl/-/mdurl-1.0.1.tgz#fe85b2ec75a59037f2adfec100fd6c601761152e"
- integrity sha1-/oWy7HWlkDfyrf7BAP1sYBdhFS4=
+ integrity sha512-/sKlQJCBYVY9Ers9hqzKou4H6V5UWc/M59TH2dvkt+84itfnq7uFOMLpOiOS4ujvHP4etln18fmIxA5R5fll0g==
media-typer@0.3.0:
version "0.3.0"
From 17cb749f0ba75937014205da96ea25ad96f160e1 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Thu, 6 Jun 2024 14:21:11 +0000
Subject: [PATCH 082/130] chore(release): cut 26.7.0 [skip ci]
# [26.7.0](https://github.com/dhis2/analytics/compare/v26.6.14...v26.7.0) (2024-06-06)
### Features
* rich text and user mention components (DHIS2-15522) ([#1525](https://github.com/dhis2/analytics/issues/1525)) ([5681126](https://github.com/dhis2/analytics/commit/5681126100d7a8ad06a81cf3c0cd2db4841a1ae4))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 43efcb3fa..aabb84e38 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+# [26.7.0](https://github.com/dhis2/analytics/compare/v26.6.14...v26.7.0) (2024-06-06)
+
+
+### Features
+
+* rich text and user mention components (DHIS2-15522) ([#1525](https://github.com/dhis2/analytics/issues/1525)) ([5681126](https://github.com/dhis2/analytics/commit/5681126100d7a8ad06a81cf3c0cd2db4841a1ae4))
+
## [26.6.14](https://github.com/dhis2/analytics/compare/v26.6.13...v26.6.14) (2024-06-03)
diff --git a/package.json b/package.json
index 57d596dfc..6d0f96c4f 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.6.14",
+ "version": "26.7.0",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 5afb945ce6a9efa4e748475ef51710272cd0f417 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 9 Jun 2024 03:42:01 +0200
Subject: [PATCH 083/130] fix(translations): sync translations from transifex
(master)
Automatically merged.
---
i18n/ne.po | 77 +++++++++++++++++++++++++++---------------------------
1 file changed, 39 insertions(+), 38 deletions(-)
diff --git a/i18n/ne.po b/i18n/ne.po
index 8539eeaf3..f3d1d4695 100644
--- a/i18n/ne.po
+++ b/i18n/ne.po
@@ -1,13 +1,14 @@
#
# Translators:
# Saroj Dhakal , 2024
+# Prabesh Guragain, 2024
#
msgid ""
msgstr ""
"Project-Id-Version: i18next-conv\n"
"POT-Creation-Date: 2024-01-25T12:05:03.360Z\n"
"PO-Revision-Date: 2020-04-28 22:05+0000\n"
-"Last-Translator: Saroj Dhakal , 2024\n"
+"Last-Translator: Prabesh Guragain, 2024\n"
"Language-Team: Nepali (https://app.transifex.com/hisp-uio/teams/100509/ne/)\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@@ -428,39 +429,6 @@ msgstr ""
msgid "Enter interpretation text"
msgstr ""
-msgid "Bold text"
-msgstr ""
-
-msgid "Italic text"
-msgstr ""
-
-msgid "Link to a URL"
-msgstr ""
-
-msgid "Mention a user"
-msgstr ""
-
-msgid "Add emoji"
-msgstr ""
-
-msgid "Preview"
-msgstr ""
-
-msgid "Back to write mode"
-msgstr ""
-
-msgid "Too many results. Try refining the search."
-msgstr ""
-
-msgid "Search for a user"
-msgstr ""
-
-msgid "Searching for \"{{- searchText}}\""
-msgstr ""
-
-msgid "No results found"
-msgstr "कुनै पनि नतिजा भेटिएन"
-
msgid "Not available offline"
msgstr ""
@@ -649,7 +617,7 @@ msgid "Select year"
msgstr ""
msgid "Period"
-msgstr ""
+msgstr "अबधि"
msgid "Selected Periods"
msgstr ""
@@ -664,7 +632,7 @@ msgid "No periods selected"
msgstr ""
msgid "Daily"
-msgstr ""
+msgstr "दैनिक"
msgid "Weekly"
msgstr ""
@@ -715,10 +683,10 @@ msgid "Financial year (Start April)"
msgstr ""
msgid "Today"
-msgstr ""
+msgstr "आज"
msgid "Yesterday"
-msgstr ""
+msgstr "हिजो"
msgid "Last 3 days"
msgstr ""
@@ -867,6 +835,27 @@ msgstr ""
msgid "Years"
msgstr ""
+msgid "Bold text"
+msgstr ""
+
+msgid "Italic text"
+msgstr ""
+
+msgid "Link to a URL"
+msgstr ""
+
+msgid "Mention a user"
+msgstr ""
+
+msgid "Add emoji"
+msgstr ""
+
+msgid "Preview"
+msgstr ""
+
+msgid "Back to write mode"
+msgstr ""
+
msgid "Interpretations and details"
msgstr ""
@@ -897,6 +886,18 @@ msgstr ""
msgid "Retry"
msgstr ""
+msgid "Too many results. Try refining the search."
+msgstr ""
+
+msgid "Search for a user"
+msgstr ""
+
+msgid "Searching for \"{{- searchText}}\""
+msgstr ""
+
+msgid "No results found"
+msgstr "कुनै पनि नतिजा भेटिएन"
+
msgid "Series"
msgstr ""
From f5d88447b55eb92efec8b741254ed9efd8807a26 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 9 Jun 2024 01:45:35 +0000
Subject: [PATCH 084/130] chore(release): cut 26.7.1 [skip ci]
## [26.7.1](https://github.com/dhis2/analytics/compare/v26.7.0...v26.7.1) (2024-06-09)
### Bug Fixes
* **translations:** sync translations from transifex (master) ([5afb945](https://github.com/dhis2/analytics/commit/5afb945ce6a9efa4e748475ef51710272cd0f417))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index aabb84e38..732deeb94 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.7.1](https://github.com/dhis2/analytics/compare/v26.7.0...v26.7.1) (2024-06-09)
+
+
+### Bug Fixes
+
+* **translations:** sync translations from transifex (master) ([5afb945](https://github.com/dhis2/analytics/commit/5afb945ce6a9efa4e748475ef51710272cd0f417))
+
# [26.7.0](https://github.com/dhis2/analytics/compare/v26.6.14...v26.7.0) (2024-06-06)
diff --git a/package.json b/package.json
index 6d0f96c4f..9fa48ba72 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.0",
+ "version": "26.7.1",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From d41b9005bc2c88bd5b499c1d6b981e9ef5774b81 Mon Sep 17 00:00:00 2001
From: Jen Jones Arnesen
Date: Tue, 11 Jun 2024 15:11:23 +0200
Subject: [PATCH 085/130] chore: new github workflow that copies build of all
non-prod branches to d2-ci (#1676)
Every branch that is not listed as one of the prod branches (from node-publish.yml)
will now have it's build pushed to d2-ci for every pushed commit.
We can then use these builds during development and testing.
Changes to README
*remove build badges for versions that are no longer supported
*add docs about how to use the build
New gh workflow file
after building the lib, use yarn pack to create the correct structure of the packaged lib.
Then unzip the result and push that to d2-ci, which can then be installed by the consuming apps.
---
.github/workflows/copy-build-to-d2-ci.yml | 45 +++++++++++++++++++++
README.md | 48 ++++++++++++++---------
2 files changed, 74 insertions(+), 19 deletions(-)
create mode 100644 .github/workflows/copy-build-to-d2-ci.yml
diff --git a/.github/workflows/copy-build-to-d2-ci.yml b/.github/workflows/copy-build-to-d2-ci.yml
new file mode 100644
index 000000000..0681e7e91
--- /dev/null
+++ b/.github/workflows/copy-build-to-d2-ci.yml
@@ -0,0 +1,45 @@
+name: Copy build to d2-ci
+
+on:
+ push:
+ branches-ignore:
+ - master
+ - next
+ - next-major
+ - alpha
+ - beta
+ - '[0-9]+.x'
+ - '[0-9]+.x.x'
+ - '[0-9]+.[0-9]+.x'
+
+env:
+ GH_TOKEN: ${{secrets.DHIS2_BOT_GITHUB_TOKEN}}
+
+jobs:
+ copy-to-d2-ci:
+ runs-on: ubuntu-latest
+ steps:
+ - name: Checkout code
+ uses: actions/checkout@v3
+ with:
+ token: ${{env.GH_TOKEN}}
+
+ - name: Set up Node.js
+ uses: actions/setup-node@v1
+ with:
+ node-version: '16.x'
+
+ - name: Install dependencies
+ run: yarn install --frozen-lockfile
+
+ - name: Build package
+ run: yarn build
+
+ - name: Pack and unpack the build to a directory named 'package'
+ run: yarn pack --filename output.tgz && tar -xzf output.tgz
+
+ - name: Copy package to d2-ci
+ uses: dhis2/deploy-build@master
+ with:
+ build-dir: package
+ github-token: ${{env.GH_TOKEN}}
diff --git a/README.md b/README.md
index 765527a1a..e39d92a55 100644
--- a/README.md
+++ b/README.md
@@ -3,23 +3,8 @@
**master**
[![Test](https://github.com/dhis2/analytics/actions/workflows/node-test.yml/badge.svg)](https://github.com/dhis2/analytics/actions/workflows/node-test.yml) [![DHIS2: Release](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml/badge.svg)](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml)
-**21.x**
-[![Test](https://github.com/dhis2/analytics/actions/workflows/node-test.yml/badge.svg?branch=21.x)](https://github.com/dhis2/analytics/actions/workflows/node-test.yml) [![DHIS2: Release](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml/badge.svg?branch=21.x)](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml)
-
-**20.x**
-[![Test](https://github.com/dhis2/analytics/actions/workflows/node-test.yml/badge.svg?branch=20.x)](https://github.com/dhis2/analytics/actions/workflows/node-test.yml) [![DHIS2: Release](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml/badge.svg?branch=20.x)](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml)
-
-**16.x**
-[![Test](https://github.com/dhis2/analytics/actions/workflows/node-test.yml/badge.svg?branch=16.x)](https://github.com/dhis2/analytics/actions/workflows/node-test.yml) [![DHIS2: Release](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml/badge.svg?branch=16.x)](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml)
-
-**11.0.x**
-[![Test](https://github.com/dhis2/analytics/actions/workflows/node-test.yml/badge.svg?branch=11.0.x)](https://github.com/dhis2/analytics/actions/workflows/node-test.yml) [![DHIS2: Release](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml/badge.svg?branch=11.0.x)](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml)
-
-**4.x**
-[![Test](https://github.com/dhis2/analytics/actions/workflows/node-test.yml/badge.svg?branch=4.x)](https://github.com/dhis2/analytics/actions/workflows/node-test.yml) [![DHIS2: Release](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml/badge.svg?branch=4.x)](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml)
-
-**2.4.x**
-[![Test](https://github.com/dhis2/analytics/actions/workflows/node-test.yml/badge.svg?branch=2.4.x)](https://github.com/dhis2/analytics/actions/workflows/node-test.yml) [![DHIS2: Release](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml/badge.svg?branch=2.4.x)](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml)
+**24.x**
+[![Test](https://github.com/dhis2/analytics/actions/workflows/node-test.yml/badge.svg?branch=24.x)](https://github.com/dhis2/analytics/actions/workflows/node-test.yml) [![DHIS2: Release](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml/badge.svg?branch=24.x)](https://github.com/dhis2/analytics/actions/workflows/node-publish.yml)
## Overview
@@ -28,6 +13,7 @@ The analytics library contains components and modules that are used in DHIS 2 an
- [dhis2/dashboards-app](https://github.com/dhis2/dashboards-app)
- [dhis2/data-visualizer-app](https://github.com/dhis2/data-visualizer-app)
- [dhis2/maps-app](https://github.com/dhis2/maps-app)
+- [dhis2/line-listing-app](https://github.com/dhis2/line-listing-app)
[Module layout documentation](./docs/module-layout.md)
@@ -35,7 +21,7 @@ The analytics library contains components and modules that are used in DHIS 2 an
The analytics package is published to npm as @dhis2/analytics.
-To publish, simply mark the commit using [semantic release terminology](https://github.com/angular/angular.js/blob/master/DEVELOPERS.md#-git-commit-guidelines) (see notes below for branch-specific restrictions). Once committed, github actions will take care of publishing the new version to npm.
+To publish, mark the commit using [semantic release terminology](https://github.com/angular/angular.js/blob/master/DEVELOPERS.md#-git-commit-guidelines) (see notes below for branch-specific restrictions). Once committed, github actions will take care of publishing the new version to npm.
### master branch
@@ -43,7 +29,31 @@ The master branch follows semantic versioning according to spec.
### .x branches
-Commits to .x branches (e.g. 16.x) cannot trigger a major version bump, even if it is technically a breaking change. This is because the next version has already been published. Additionally, branches that use .x for the patch version (e.g. 11.0.x, 2.4.x), cannot trigger a minor version bump. In the unlikely case that you need to commit a change that would trigger a version bump that's not possible, you will have to mark it to only trigger a patch or minor bump respectively, then make sure to update the apps that are locked to the .x version of analytics
+Commits to .x branches (e.g. 24.x) cannot trigger a major version bump, even if it is technically a breaking change. This is because the next version has already been published. Additionally, branches that use .x for the patch version (e.g. 11.0.x, 2.4.x), cannot trigger a minor version bump. In the unlikely case that you need to commit a change that would trigger a version bump that's not possible, you will have to mark it to only trigger a patch or minor bump respectively, then make sure to update the apps that are locked to the .x version of analytics
+
+## Publishing pre-release versions during app development
+
+Builds for all non-production branches are automatically copied to [d2-ci/analytics](https://github.com/d2-ci/analytics) for use during development and testing, prior to production release.
+
+To test changes in a development branch, change the analytics dependency of package.json of the app you are testing with. There are a few options:
+
+1. point to a specific commit:
+
+```
+"dependencies": {
+ "@dhis2/analytics": "git+https://github.com/d2-ci/analytics.git#70249ebe8be39051fa10142f850de449e1ec488c",
+ ...
+}
+```
+
+2. point to a branch:
+
+```
+"dependencies": {
+ "@dhis2/analytics": "git+https://github.com/d2-ci/analytics.git#chore/some-chore",
+ ...
+}
+```
## Report an issue
From ad8c799187a8f143eb16a3f554e5e02afa4a4256 Mon Sep 17 00:00:00 2001
From: Martin
Date: Wed, 12 Jun 2024 13:06:10 +0300
Subject: [PATCH 086/130] fix: separator for hundreds, thousands and millions
is missing in the Pie charts (DHIS2-16172) (#1677)
---
src/modules/renderValue.js | 11 ++--
.../series/__tests__/pie.spec.js | 66 +++++++++++++++++++
.../adapters/dhis_highcharts/series/pie.js | 27 +++++---
3 files changed, 89 insertions(+), 15 deletions(-)
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/series/__tests__/pie.spec.js
diff --git a/src/modules/renderValue.js b/src/modules/renderValue.js
index 17e288043..a65d8a6d8 100644
--- a/src/modules/renderValue.js
+++ b/src/modules/renderValue.js
@@ -6,9 +6,7 @@ import { isNumericValueType } from './valueTypes.js'
const trimTrailingZeros = (stringValue) => stringValue.replace(/\.?0+$/, '')
-const decimalSeparator = '.'
-
-const separateDigitGroups = (stringValue, decimalSeparator) => {
+export const separateDigitGroups = (stringValue, decimalSeparator = '.') => {
const isNegative = stringValue[0] === '-'
const [integer, remainder] = stringValue.replace(/^-/, '').split('.')
@@ -68,9 +66,8 @@ export const renderValue = (value, valueType, visualization) => {
)
return (
- separateDigitGroups(stringValue, decimalSeparator).join(
- getSeparator(visualization)
- ) + '%'
+ separateDigitGroups(stringValue).join(getSeparator(visualization)) +
+ '%'
)
} else {
const stringValue = toFixedPrecisionString(
@@ -78,7 +75,7 @@ export const renderValue = (value, valueType, visualization) => {
visualization.skipRounding
)
- return separateDigitGroups(stringValue, decimalSeparator).join(
+ return separateDigitGroups(stringValue).join(
getSeparator(visualization)
)
}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/series/__tests__/pie.spec.js b/src/visualizations/config/adapters/dhis_highcharts/series/__tests__/pie.spec.js
new file mode 100644
index 000000000..eb9abac19
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/series/__tests__/pie.spec.js
@@ -0,0 +1,66 @@
+import { formatDataLabel } from '../pie.js'
+
+describe('formatDataLabel', () => {
+ it('should format data label correctly with integers', () => {
+ const result = formatDataLabel('Test', 1000, 50)
+ expect(result).toEqual(
+ 'Test
1 000 (50%)'
+ )
+ })
+
+ it('should format data label correctly with decimals', () => {
+ const result = formatDataLabel('Test', 1000.123456789, 50.1234)
+ expect(result).toEqual(
+ 'Test
1 000.123456789 (50.1%)'
+ )
+ })
+
+ it('should handle large numbers correctly', () => {
+ const result = formatDataLabel('Test', 1000000, 75.5678)
+ expect(result).toEqual(
+ 'Test
1 000 000 (75.6%)'
+ )
+ })
+
+ it('should handle small percentages correctly', () => {
+ const result = formatDataLabel('Test', 1000.000001, 0.09)
+ expect(result).toEqual(
+ 'Test
1 000.000001 (0.1%)'
+ )
+ })
+
+ it('should handle zero correctly', () => {
+ const result = formatDataLabel('Test', 0, 0)
+ expect(result).toEqual(
+ 'Test
0 (0%)'
+ )
+ })
+
+ it('should handle negative numbers correctly', () => {
+ const result = formatDataLabel('Test', -1000, -50)
+ expect(result).toEqual(
+ 'Test
-1 000 (-50%)'
+ )
+ })
+
+ it('should handle empty string as name correctly', () => {
+ const result = formatDataLabel('', 1000, 50)
+ expect(result).toEqual(
+ '
1 000 (50%)'
+ )
+ })
+
+ it('should handle undefined as name correctly', () => {
+ const result = formatDataLabel(undefined, 1000, 50)
+ expect(result).toEqual(
+ '
1 000 (50%)'
+ )
+ })
+
+ it('should handle special characters in name correctly', () => {
+ const result = formatDataLabel('Test&Test', 1000, 50)
+ expect(result).toEqual(
+ 'Test&Test
1 000 (50%)'
+ )
+ })
+})
diff --git a/src/visualizations/config/adapters/dhis_highcharts/series/pie.js b/src/visualizations/config/adapters/dhis_highcharts/series/pie.js
index 67a4e772d..b5afb2c49 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/series/pie.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/series/pie.js
@@ -1,3 +1,18 @@
+import { separateDigitGroups } from '../../../../../modules/renderValue.js'
+
+export const formatDataLabel = (name = '', y, percentage) => {
+ const value = separateDigitGroups(y.toString()).join(' ')
+ return (
+ '' +
+ name +
+ '
' +
+ value +
+ ' (' +
+ parseFloat(percentage.toFixed(1)) +
+ '%)'
+ )
+}
+
export default function (series, colors) {
return [
{
@@ -9,14 +24,10 @@ export default function (series, colors) {
dataLabels: {
enabled: true,
formatter: function () {
- return (
- '' +
- this.point.name +
- '
' +
- this.y +
- ' (' +
- this.percentage.toFixed(1) +
- ' %)'
+ return formatDataLabel(
+ this.point.name,
+ this.y,
+ this.percentage
)
},
},
From c8aed5da5a71ca8da10bc4f4537b1956711a0d39 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Wed, 12 Jun 2024 10:09:53 +0000
Subject: [PATCH 087/130] chore(release): cut 26.7.2 [skip ci]
## [26.7.2](https://github.com/dhis2/analytics/compare/v26.7.1...v26.7.2) (2024-06-12)
### Bug Fixes
* separator for hundreds, thousands and millions is missing in the Pie charts (DHIS2-16172) ([#1677](https://github.com/dhis2/analytics/issues/1677)) ([ad8c799](https://github.com/dhis2/analytics/commit/ad8c799187a8f143eb16a3f554e5e02afa4a4256))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 732deeb94..d5c66a1cd 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.7.2](https://github.com/dhis2/analytics/compare/v26.7.1...v26.7.2) (2024-06-12)
+
+
+### Bug Fixes
+
+* separator for hundreds, thousands and millions is missing in the Pie charts (DHIS2-16172) ([#1677](https://github.com/dhis2/analytics/issues/1677)) ([ad8c799](https://github.com/dhis2/analytics/commit/ad8c799187a8f143eb16a3f554e5e02afa4a4256))
+
## [26.7.1](https://github.com/dhis2/analytics/compare/v26.7.0...v26.7.1) (2024-06-09)
diff --git a/package.json b/package.json
index 9fa48ba72..b853b3d14 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.1",
+ "version": "26.7.2",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 41601383b5b918914757841791cd62c1a87ec135 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 16 Jun 2024 03:42:06 +0200
Subject: [PATCH 088/130] fix(translations): sync translations from transifex
(master)
Automatically merged.
---
i18n/fr.po | 152 ++++++++++++++++++++++++++++++-----------------------
i18n/ru.po | 119 +++++++++++++++++++++++------------------
2 files changed, 156 insertions(+), 115 deletions(-)
diff --git a/i18n/fr.po b/i18n/fr.po
index 96d50b43d..4cb619f4b 100644
--- a/i18n/fr.po
+++ b/i18n/fr.po
@@ -9,13 +9,14 @@
# Yao Selom SAKA (HISP WCA) , 2023
# Yayra Gomado , 2023
# Philip Larsen Donnelly, 2024
+# Elise Desailly, 2024
#
msgid ""
msgstr ""
"Project-Id-Version: i18next-conv\n"
-"POT-Creation-Date: 2023-09-27T14:15:13.876Z\n"
+"POT-Creation-Date: 2024-01-25T12:05:03.360Z\n"
"PO-Revision-Date: 2020-04-28 22:05+0000\n"
-"Last-Translator: Philip Larsen Donnelly, 2024\n"
+"Last-Translator: Elise Desailly, 2024\n"
"Language-Team: French (https://app.transifex.com/hisp-uio/teams/100509/fr/)\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@@ -45,13 +46,13 @@ msgid "No description"
msgstr "Aucune description"
msgid "Last updated {{time}}"
-msgstr ""
+msgstr "Dernière mise à jour à {{time}}"
msgid "Created {{time}} by {{author}}"
-msgstr ""
+msgstr "Créé à {{time}} par {{author}} "
msgid "Created {{time}}"
-msgstr ""
+msgstr "Créé à {{time}}"
msgid "Viewed {{count}} times"
msgid_plural "Viewed {{count}} times"
@@ -64,6 +65,8 @@ msgstr "Notifications"
msgid "You're subscribed and getting updates about new interpretations."
msgstr ""
+"Vous êtes abonné et recevez les mises à jour pour les nouvelles "
+"interprétations."
msgid "Unsubscribe"
msgstr ""
@@ -75,16 +78,16 @@ msgid "Subscribe"
msgstr ""
msgid "About this map"
-msgstr ""
+msgstr "À propos de cette carte"
msgid "About this line list"
msgstr ""
msgid "About this visualization"
-msgstr ""
+msgstr "À propos de cette visualisation"
msgid "This app could not retrieve required data."
-msgstr ""
+msgstr "Cette application n'a pas pu récupérer les données nécessaires."
msgid "Network error"
msgstr "Erreur réseau"
@@ -96,36 +99,38 @@ msgid "Data / New calculation"
msgstr ""
msgid "Remove item"
-msgstr ""
+msgstr "Supprimer l'élément"
msgid "Check formula"
msgstr ""
msgid "Calculation name"
-msgstr ""
+msgstr "Nom du calcul"
msgid "Shown in table headers and chart axes/legends"
msgstr ""
msgid "Delete calculation"
-msgstr ""
+msgstr "Supprimer le calcul"
msgid "Cancel"
msgstr "Annuler"
msgid "The calculation can only be saved with a valid formula"
-msgstr ""
+msgstr "Le calcul ne peut être sauvegardé qu'avec une formule correcte"
msgid "Add a name to save this calculation"
-msgstr ""
+msgstr "Ajouter un nom pour sauvegarder ce calcul"
msgid "Save calculation"
-msgstr ""
+msgstr "Sauvegarder le calcul"
msgid ""
"Are you sure you want to delete this calculation? It may be used by other "
"visualizations."
msgstr ""
+"Êtes-vous certain de vouloir supprimer ce calcul ? Il est peut être utilisé "
+"par d'autres visualisations."
msgid "Yes, delete"
msgstr "Oui, supprimer"
@@ -143,7 +148,7 @@ msgid "Data elements"
msgstr "Eléments de données"
msgid "Search by data element name"
-msgstr ""
+msgstr "Rechercher par le nom d'élément de donnée"
msgid "No data elements found for \"{{- searchTerm}}\""
msgstr "Aucun élément de données trouvé pour \"{{- searchTerm}}\""
@@ -157,11 +162,14 @@ msgid ""
msgstr ""
msgid "Math operators"
-msgstr ""
+msgstr "Opérateurs mathématiques"
msgid "Data Type"
msgstr "Type de données"
+msgid "Only {{dataType}} can be used in {{visType}}"
+msgstr ""
+
msgid "All types"
msgstr "Tous les types"
@@ -192,6 +200,9 @@ msgstr "Aucun éléments de données événement trouvé"
msgid "No program indicators found"
msgstr "Aucun Indicateurs de programme trouvé"
+msgid "No calculations found"
+msgstr "Aucun calcul trouvé"
+
msgid "No indicators found for \"{{- searchTerm}}\""
msgstr "Aucun indicateur trouvé pour \"{{- searchTerm}}\""
@@ -204,6 +215,9 @@ msgstr "Aucune donnée événement retrouvée pour \"{{- searchTerm}}\""
msgid "No program indicators found for \"{{- searchTerm}}\""
msgstr "Aucun Indicateur de programme trouvé pour \"{{- searchTerm}}\""
+msgid "No calculations found for \"{{- searchTerm}}\""
+msgstr ""
+
msgid "Nothing found for \"{{- searchTerm}}\""
msgstr "Rien retrouvé pour \"{{- searchTerm}}\""
@@ -250,7 +264,7 @@ msgid "All items"
msgstr "Tous les items"
msgid "Automatically include all items"
-msgstr ""
+msgstr "Inclure tous les éléments automatiquement"
msgid ""
"Select all {{- dimensionTitle}} items. With this option, new items added in "
@@ -358,7 +372,7 @@ msgid "Delete failed"
msgstr "Échec de la suppression"
msgid "Could not update comment"
-msgstr ""
+msgstr "Échec de l'actualisation du commentaire"
msgid "Enter comment text"
msgstr ""
@@ -370,15 +384,17 @@ msgid "Viewing interpretation: {{- visualisationName}}"
msgstr ""
msgid "Could not load interpretation"
-msgstr ""
+msgstr "Échec du chargement de l'interprétation"
msgid ""
"The interpretation couldn’t be displayed. Try again or contact your system "
"administrator."
msgstr ""
+"L'interprétation n'a pas pu être affichée. Veuillez réessayer ou contacter "
+"votre administrateur système."
msgid "Hide interpretation"
-msgstr ""
+msgstr "Masquer l'interprétation"
msgid "Write an interpretation"
msgstr "Ecrire une interprétation"
@@ -403,7 +419,7 @@ msgstr[1] "{{count}} réponses"
msgstr[2] "{{count}} réponses"
msgid "View replies"
-msgstr ""
+msgstr "Voir les réponses"
msgid "Unlike"
msgstr "Je n'aime plus"
@@ -411,54 +427,24 @@ msgstr "Je n'aime plus"
msgid "Like"
msgstr "J'aime"
-msgid "Share"
-msgstr "Partager"
-
msgid "See interpretation"
msgstr ""
+msgid "Open in app"
+msgstr "Ouvrir dans l'application"
+
+msgid "Share"
+msgstr "Partager"
+
msgid "Manage sharing"
msgstr "Gérer le partage"
msgid "Could not update interpretation"
-msgstr ""
+msgstr "Échec de l'actualisation de l'interprétation"
msgid "Enter interpretation text"
msgstr ""
-msgid "Bold text"
-msgstr ""
-
-msgid "Italic text"
-msgstr ""
-
-msgid "Link to a URL"
-msgstr ""
-
-msgid "Mention a user"
-msgstr ""
-
-msgid "Add emoji"
-msgstr ""
-
-msgid "Preview"
-msgstr "Aperçu"
-
-msgid "Back to write mode"
-msgstr ""
-
-msgid "Too many results. Try refining the search."
-msgstr ""
-
-msgid "Search for a user"
-msgstr ""
-
-msgid "Searching for \"{{- searchText}}\""
-msgstr ""
-
-msgid "No results found"
-msgstr "Aucun résultat trouvé"
-
msgid "Not available offline"
msgstr "Non disponible hors ligne"
@@ -543,13 +529,13 @@ msgid "New visualization"
msgstr ""
msgid "Open a map"
-msgstr ""
+msgstr "Ouvrir une carte"
msgid "Loading maps"
-msgstr ""
+msgstr "Chargement des cartes"
msgid "Couldn't load maps"
-msgstr ""
+msgstr "Échec du chargement des cartes"
msgid ""
"There was a problem loading maps. Try again or contact your system "
@@ -557,7 +543,7 @@ msgid ""
msgstr ""
msgid "No maps found. Click New map to get started."
-msgstr ""
+msgstr "Aucune carte trouvée. Cliquez sur Nouvelle carte pour commencer."
msgid ""
"No maps found. Try adjusting your search or filter options to find what "
@@ -652,15 +638,15 @@ msgstr "Sélectionnez année"
msgid "Period"
msgstr "Période"
+msgid "Selected Periods"
+msgstr "Périodes sélectionnées"
+
msgid "Relative periods"
msgstr "Périodes relatives"
msgid "Fixed periods"
msgstr "Périodes fixes"
-msgid "Selected Periods"
-msgstr "Périodes sélectionnées"
-
msgid "No periods selected"
msgstr "Aucune périodes n'est sélectionnée"
@@ -868,6 +854,27 @@ msgstr "Années fiscales"
msgid "Years"
msgstr "Années"
+msgid "Bold text"
+msgstr "Texte en gras"
+
+msgid "Italic text"
+msgstr ""
+
+msgid "Link to a URL"
+msgstr ""
+
+msgid "Mention a user"
+msgstr ""
+
+msgid "Add emoji"
+msgstr ""
+
+msgid "Preview"
+msgstr "Aperçu"
+
+msgid "Back to write mode"
+msgstr ""
+
msgid "Interpretations and details"
msgstr ""
@@ -898,6 +905,18 @@ msgstr ""
msgid "Retry"
msgstr ""
+msgid "Too many results. Try refining the search."
+msgstr ""
+
+msgid "Search for a user"
+msgstr ""
+
+msgid "Searching for \"{{- searchText}}\""
+msgstr ""
+
+msgid "No results found"
+msgstr "Aucun résultat trouvé"
+
msgid "Series"
msgstr "Séries"
@@ -1162,6 +1181,9 @@ msgstr "Dispersion"
msgid "Single value"
msgstr "Valeur unique"
+msgid "Outlier table"
+msgstr ""
+
msgid "All charts"
msgstr ""
diff --git a/i18n/ru.po b/i18n/ru.po
index 9e8428fc8..7bc8a734d 100644
--- a/i18n/ru.po
+++ b/i18n/ru.po
@@ -1,18 +1,18 @@
#
# Translators:
-# Yury Rogachev , 2020
# Valeriu Plesca , 2021
# Wanda , 2022
# Viktor Varland , 2022
# Ulanbek Abakirov , 2022
-# phil_dhis2, 2023
+# Philip Larsen Donnelly, 2023
+# Yury Rogachev , 2024
#
msgid ""
msgstr ""
"Project-Id-Version: i18next-conv\n"
-"POT-Creation-Date: 2023-07-06T08:30:33.216Z\n"
+"POT-Creation-Date: 2024-01-25T12:05:03.360Z\n"
"PO-Revision-Date: 2020-04-28 22:05+0000\n"
-"Last-Translator: phil_dhis2, 2023\n"
+"Last-Translator: Yury Rogachev , 2024\n"
"Language-Team: Russian (https://app.transifex.com/hisp-uio/teams/100509/ru/)\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@@ -160,6 +160,9 @@ msgstr ""
msgid "Data Type"
msgstr "Тип данных"
+msgid "Only {{dataType}} can be used in {{visType}}"
+msgstr ""
+
msgid "All types"
msgstr "Все типы"
@@ -190,6 +193,9 @@ msgstr ""
msgid "No program indicators found"
msgstr ""
+msgid "No calculations found"
+msgstr ""
+
msgid "No indicators found for \"{{- searchTerm}}\""
msgstr ""
@@ -202,6 +208,9 @@ msgstr ""
msgid "No program indicators found for \"{{- searchTerm}}\""
msgstr ""
+msgid "No calculations found for \"{{- searchTerm}}\""
+msgstr ""
+
msgid "Nothing found for \"{{- searchTerm}}\""
msgstr ""
@@ -341,7 +350,7 @@ msgid "map"
msgstr "Карта"
msgid "visualization"
-msgstr ""
+msgstr "визуализация"
msgid "Edit"
msgstr "Редактировать"
@@ -381,6 +390,10 @@ msgstr ""
msgid "Write an interpretation"
msgstr "Написать перевод"
+msgid ""
+"Other people viewing this interpretation in the future may see more data."
+msgstr ""
+
msgid "Post interpretation"
msgstr ""
@@ -392,10 +405,10 @@ msgstr "Ответить"
msgid "{{count}} replies"
msgid_plural "{{count}} replies"
-msgstr[0] ""
-msgstr[1] ""
-msgstr[2] ""
-msgstr[3] ""
+msgstr[0] "{{count}} ответ"
+msgstr[1] "{{count}} отвечает"
+msgstr[2] "{{count}} отвечает"
+msgstr[3] "{{count}} ответов"
msgid "View replies"
msgstr ""
@@ -406,12 +419,15 @@ msgstr "Не нравится"
msgid "Like"
msgstr "Нравится"
-msgid "Share"
-msgstr "Поделиться"
-
msgid "See interpretation"
msgstr ""
+msgid "Open in app"
+msgstr ""
+
+msgid "Share"
+msgstr "Поделиться"
+
msgid "Manage sharing"
msgstr "Управление совместным доступом"
@@ -421,41 +437,8 @@ msgstr ""
msgid "Enter interpretation text"
msgstr ""
-msgid "Bold text"
-msgstr ""
-
-msgid "Italic text"
-msgstr ""
-
-msgid "Link to a URL"
-msgstr ""
-
-msgid "Mention a user"
-msgstr ""
-
-msgid "Add emoji"
-msgstr ""
-
-msgid "Preview"
-msgstr "Предварительный просмотр"
-
-msgid "Back to write mode"
-msgstr ""
-
-msgid "Too many results. Try refining the search."
-msgstr ""
-
-msgid "Search for a user"
-msgstr ""
-
-msgid "Searching for \"{{- searchText}}\""
-msgstr ""
-
-msgid "No results found"
-msgstr "Результаты не найдены"
-
msgid "Not available offline"
-msgstr ""
+msgstr "Недоступно в автономном режиме"
msgid "Created by"
msgstr "Создано"
@@ -650,15 +633,15 @@ msgstr "Выбрать год"
msgid "Period"
msgstr "Период"
+msgid "Selected Periods"
+msgstr "Выбранные периоды"
+
msgid "Relative periods"
msgstr "Соответствующие периоды"
msgid "Fixed periods"
msgstr "Фиксированные периоды"
-msgid "Selected Periods"
-msgstr "Выбранные периоды"
-
msgid "No periods selected"
msgstr "Периоды не выбраны"
@@ -866,6 +849,27 @@ msgstr "Финансовые годы"
msgid "Years"
msgstr "Годы"
+msgid "Bold text"
+msgstr ""
+
+msgid "Italic text"
+msgstr ""
+
+msgid "Link to a URL"
+msgstr ""
+
+msgid "Mention a user"
+msgstr ""
+
+msgid "Add emoji"
+msgstr ""
+
+msgid "Preview"
+msgstr "Предварительный просмотр"
+
+msgid "Back to write mode"
+msgstr ""
+
msgid "Interpretations and details"
msgstr ""
@@ -896,6 +900,18 @@ msgstr ""
msgid "Retry"
msgstr ""
+msgid "Too many results. Try refining the search."
+msgstr ""
+
+msgid "Search for a user"
+msgstr ""
+
+msgid "Searching for \"{{- searchText}}\""
+msgstr ""
+
+msgid "No results found"
+msgstr "Результаты не найдены"
+
msgid "Series"
msgstr "Ряды"
@@ -1155,11 +1171,14 @@ msgid "Radar"
msgstr "Радиальная"
msgid "Scatter"
-msgstr ""
+msgstr "Рассеивание"
msgid "Single value"
msgstr "Одиночное значение"
+msgid "Outlier table"
+msgstr ""
+
msgid "All charts"
msgstr ""
From 8ec2809589d960a9cf3fa8de771a98ef6ed072d1 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 16 Jun 2024 01:45:51 +0000
Subject: [PATCH 089/130] chore(release): cut 26.7.3 [skip ci]
## [26.7.3](https://github.com/dhis2/analytics/compare/v26.7.2...v26.7.3) (2024-06-16)
### Bug Fixes
* **translations:** sync translations from transifex (master) ([4160138](https://github.com/dhis2/analytics/commit/41601383b5b918914757841791cd62c1a87ec135))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index d5c66a1cd..fd83ffbd3 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.7.3](https://github.com/dhis2/analytics/compare/v26.7.2...v26.7.3) (2024-06-16)
+
+
+### Bug Fixes
+
+* **translations:** sync translations from transifex (master) ([4160138](https://github.com/dhis2/analytics/commit/41601383b5b918914757841791cd62c1a87ec135))
+
## [26.7.2](https://github.com/dhis2/analytics/compare/v26.7.1...v26.7.2) (2024-06-12)
diff --git a/package.json b/package.json
index b853b3d14..d1220c973 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.2",
+ "version": "26.7.3",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 44b753a5dc618d20e92a056691819ea5cee351b3 Mon Sep 17 00:00:00 2001
From: Hendrik de Graaf
Date: Thu, 20 Jun 2024 12:51:14 +0200
Subject: [PATCH 090/130] fix(pivot-table): use a scoped base selector and
global sub selectors (#1681)
Co-authored-by: Jen Jones Arnesen
---
.../PivotTable/styles/PivotTable.style.js | 28 ++++++++++---------
1 file changed, 15 insertions(+), 13 deletions(-)
diff --git a/src/components/PivotTable/styles/PivotTable.style.js b/src/components/PivotTable/styles/PivotTable.style.js
index 88c817042..60466810a 100644
--- a/src/components/PivotTable/styles/PivotTable.style.js
+++ b/src/components/PivotTable/styles/PivotTable.style.js
@@ -10,14 +10,14 @@ import {
FONT_SIZE_LARGE,
} from '../../../modules/pivotTable/pivotTableConstants.js'
-export const table = css.global`
+export const table = css`
div.pivot-table-container {
font-family: 'Roboto', Arial, sans-serif;
overflow: auto;
color: ${colors.grey900};
}
- table {
+ div.pivot-table-container :global(table) {
border-spacing: 0;
white-space: nowrap;
box-sizing: border-box;
@@ -26,35 +26,37 @@ export const table = css.global`
border-width: 1px 1px 0 0;
}
- table.fixed-headers {
+ div.pivot-table-container :global(table.fixed-headers) {
border-width: 0 0 0 1px;
}
- table.fixed-headers tr th,
- table.fixed-headers tr td {
+ div.pivot-table-container :global(table.fixed-headers tr th),
+ div.pivot-table-container :global(table.fixed-headers tr td) {
border-width: 0 1px 1px 0;
}
- table.fixed-column-headers {
+ div.pivot-table-container :global(table.fixed-column-headers) {
border-width: 0 1px 0 0;
}
- table.fixed-column-headers tr th,
- table.fixed-column-headers tr td {
+ div.pivot-table-container :global(table.fixed-column-headers tr th),
+ div.pivot-table-container :global(table.fixed-column-headers tr td) {
border-width: 0 0 1px 1px;
}
- table.fixed-headers thead tr:first-of-type th,
- table.fixed-column-headers thead tr:first-of-type th {
+ div.pivot-table-container
+ :global(table.fixed-headers thead tr:first-of-type th),
+ div.pivot-table-container
+ :global(table.fixed-column-headers thead tr:first-of-type th) {
border-top: 1px solid ${BORDER_COLOR};
}
- table.fixed-row-headers {
+ div.pivot-table-container :global(table.fixed-row-headers) {
border-width: 0 0 1px 1px;
}
- table.fixed-row-headers tr th,
- table.fixed-row-headers tr td {
+ div.pivot-table-container :global(table.fixed-row-headers tr th),
+ div.pivot-table-container :global(table.fixed-row-headers tr td) {
border-width: 1px 1px 0 0;
}
`
From 6d73f146f605b3163f105272b3939616893f3996 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Thu, 20 Jun 2024 10:54:49 +0000
Subject: [PATCH 091/130] chore(release): cut 26.7.4 [skip ci]
## [26.7.4](https://github.com/dhis2/analytics/compare/v26.7.3...v26.7.4) (2024-06-20)
### Bug Fixes
* **pivot-table:** use a scoped base selector and global sub selectors ([#1681](https://github.com/dhis2/analytics/issues/1681)) ([44b753a](https://github.com/dhis2/analytics/commit/44b753a5dc618d20e92a056691819ea5cee351b3))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index fd83ffbd3..d4a911d2c 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.7.4](https://github.com/dhis2/analytics/compare/v26.7.3...v26.7.4) (2024-06-20)
+
+
+### Bug Fixes
+
+* **pivot-table:** use a scoped base selector and global sub selectors ([#1681](https://github.com/dhis2/analytics/issues/1681)) ([44b753a](https://github.com/dhis2/analytics/commit/44b753a5dc618d20e92a056691819ea5cee351b3))
+
## [26.7.3](https://github.com/dhis2/analytics/compare/v26.7.2...v26.7.3) (2024-06-16)
diff --git a/package.json b/package.json
index d1220c973..046712a78 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.3",
+ "version": "26.7.4",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From b3a48ba8cff9956468a2670c0dda16549247bd18 Mon Sep 17 00:00:00 2001
From: Edoardo Sabadelli
Date: Tue, 25 Jun 2024 11:26:11 +0200
Subject: [PATCH 092/130] fix: update multicalendar dep for translations
(DHIS2-16904) (#1685)
* fix: update multicalendar dep for translations (DHIS2-16904)
* fix: update multi calendar dep for translations (DHIS2-16904)
* test: update snapshot
---
package.json | 2 +-
.../__snapshots__/fixedPeriods.spec.js.snap | 1602 +++++++++++++++++
yarn.lock | 38 +-
3 files changed, 1626 insertions(+), 16 deletions(-)
diff --git a/package.json b/package.json
index 046712a78..06180396b 100644
--- a/package.json
+++ b/package.json
@@ -59,7 +59,7 @@
"styled-jsx": "^4.0.1"
},
"dependencies": {
- "@dhis2/multi-calendar-dates": "1.0.0",
+ "@dhis2/multi-calendar-dates": "^1.2.2",
"@dnd-kit/core": "^6.0.7",
"@dnd-kit/sortable": "^7.0.2",
"@dnd-kit/utilities": "^3.2.1",
diff --git a/src/components/PeriodDimension/__tests__/__snapshots__/fixedPeriods.spec.js.snap b/src/components/PeriodDimension/__tests__/__snapshots__/fixedPeriods.spec.js.snap
index be670cf0c..69aaa2343 100644
--- a/src/components/PeriodDimension/__tests__/__snapshots__/fixedPeriods.spec.js.snap
+++ b/src/components/PeriodDimension/__tests__/__snapshots__/fixedPeriods.spec.js.snap
@@ -6,185 +6,237 @@ Object {
"name": "Bi-weekly",
"options": Array [
Object {
+ "displayName": "Bi-Week 1 - 2013-12-30 - 2014-01-12",
"endDate": "2014-01-12",
"id": "2014BiW1",
"iso": "2014BiW1",
"name": "Bi-Week 1 - 2013-12-30 - 2014-01-12",
+ "periodType": "BIWEEKLY",
"startDate": "2013-12-30",
},
Object {
+ "displayName": "Bi-Week 2 - 2014-01-13 - 2014-01-26",
"endDate": "2014-01-26",
"id": "2014BiW2",
"iso": "2014BiW2",
"name": "Bi-Week 2 - 2014-01-13 - 2014-01-26",
+ "periodType": "BIWEEKLY",
"startDate": "2014-01-13",
},
Object {
+ "displayName": "Bi-Week 3 - 2014-01-27 - 2014-02-09",
"endDate": "2014-02-09",
"id": "2014BiW3",
"iso": "2014BiW3",
"name": "Bi-Week 3 - 2014-01-27 - 2014-02-09",
+ "periodType": "BIWEEKLY",
"startDate": "2014-01-27",
},
Object {
+ "displayName": "Bi-Week 4 - 2014-02-10 - 2014-02-23",
"endDate": "2014-02-23",
"id": "2014BiW4",
"iso": "2014BiW4",
"name": "Bi-Week 4 - 2014-02-10 - 2014-02-23",
+ "periodType": "BIWEEKLY",
"startDate": "2014-02-10",
},
Object {
+ "displayName": "Bi-Week 5 - 2014-02-24 - 2014-03-09",
"endDate": "2014-03-09",
"id": "2014BiW5",
"iso": "2014BiW5",
"name": "Bi-Week 5 - 2014-02-24 - 2014-03-09",
+ "periodType": "BIWEEKLY",
"startDate": "2014-02-24",
},
Object {
+ "displayName": "Bi-Week 6 - 2014-03-10 - 2014-03-23",
"endDate": "2014-03-23",
"id": "2014BiW6",
"iso": "2014BiW6",
"name": "Bi-Week 6 - 2014-03-10 - 2014-03-23",
+ "periodType": "BIWEEKLY",
"startDate": "2014-03-10",
},
Object {
+ "displayName": "Bi-Week 7 - 2014-03-24 - 2014-04-06",
"endDate": "2014-04-06",
"id": "2014BiW7",
"iso": "2014BiW7",
"name": "Bi-Week 7 - 2014-03-24 - 2014-04-06",
+ "periodType": "BIWEEKLY",
"startDate": "2014-03-24",
},
Object {
+ "displayName": "Bi-Week 8 - 2014-04-07 - 2014-04-20",
"endDate": "2014-04-20",
"id": "2014BiW8",
"iso": "2014BiW8",
"name": "Bi-Week 8 - 2014-04-07 - 2014-04-20",
+ "periodType": "BIWEEKLY",
"startDate": "2014-04-07",
},
Object {
+ "displayName": "Bi-Week 9 - 2014-04-21 - 2014-05-04",
"endDate": "2014-05-04",
"id": "2014BiW9",
"iso": "2014BiW9",
"name": "Bi-Week 9 - 2014-04-21 - 2014-05-04",
+ "periodType": "BIWEEKLY",
"startDate": "2014-04-21",
},
Object {
+ "displayName": "Bi-Week 10 - 2014-05-05 - 2014-05-18",
"endDate": "2014-05-18",
"id": "2014BiW10",
"iso": "2014BiW10",
"name": "Bi-Week 10 - 2014-05-05 - 2014-05-18",
+ "periodType": "BIWEEKLY",
"startDate": "2014-05-05",
},
Object {
+ "displayName": "Bi-Week 11 - 2014-05-19 - 2014-06-01",
"endDate": "2014-06-01",
"id": "2014BiW11",
"iso": "2014BiW11",
"name": "Bi-Week 11 - 2014-05-19 - 2014-06-01",
+ "periodType": "BIWEEKLY",
"startDate": "2014-05-19",
},
Object {
+ "displayName": "Bi-Week 12 - 2014-06-02 - 2014-06-15",
"endDate": "2014-06-15",
"id": "2014BiW12",
"iso": "2014BiW12",
"name": "Bi-Week 12 - 2014-06-02 - 2014-06-15",
+ "periodType": "BIWEEKLY",
"startDate": "2014-06-02",
},
Object {
+ "displayName": "Bi-Week 13 - 2014-06-16 - 2014-06-29",
"endDate": "2014-06-29",
"id": "2014BiW13",
"iso": "2014BiW13",
"name": "Bi-Week 13 - 2014-06-16 - 2014-06-29",
+ "periodType": "BIWEEKLY",
"startDate": "2014-06-16",
},
Object {
+ "displayName": "Bi-Week 14 - 2014-06-30 - 2014-07-13",
"endDate": "2014-07-13",
"id": "2014BiW14",
"iso": "2014BiW14",
"name": "Bi-Week 14 - 2014-06-30 - 2014-07-13",
+ "periodType": "BIWEEKLY",
"startDate": "2014-06-30",
},
Object {
+ "displayName": "Bi-Week 15 - 2014-07-14 - 2014-07-27",
"endDate": "2014-07-27",
"id": "2014BiW15",
"iso": "2014BiW15",
"name": "Bi-Week 15 - 2014-07-14 - 2014-07-27",
+ "periodType": "BIWEEKLY",
"startDate": "2014-07-14",
},
Object {
+ "displayName": "Bi-Week 16 - 2014-07-28 - 2014-08-10",
"endDate": "2014-08-10",
"id": "2014BiW16",
"iso": "2014BiW16",
"name": "Bi-Week 16 - 2014-07-28 - 2014-08-10",
+ "periodType": "BIWEEKLY",
"startDate": "2014-07-28",
},
Object {
+ "displayName": "Bi-Week 17 - 2014-08-11 - 2014-08-24",
"endDate": "2014-08-24",
"id": "2014BiW17",
"iso": "2014BiW17",
"name": "Bi-Week 17 - 2014-08-11 - 2014-08-24",
+ "periodType": "BIWEEKLY",
"startDate": "2014-08-11",
},
Object {
+ "displayName": "Bi-Week 18 - 2014-08-25 - 2014-09-07",
"endDate": "2014-09-07",
"id": "2014BiW18",
"iso": "2014BiW18",
"name": "Bi-Week 18 - 2014-08-25 - 2014-09-07",
+ "periodType": "BIWEEKLY",
"startDate": "2014-08-25",
},
Object {
+ "displayName": "Bi-Week 19 - 2014-09-08 - 2014-09-21",
"endDate": "2014-09-21",
"id": "2014BiW19",
"iso": "2014BiW19",
"name": "Bi-Week 19 - 2014-09-08 - 2014-09-21",
+ "periodType": "BIWEEKLY",
"startDate": "2014-09-08",
},
Object {
+ "displayName": "Bi-Week 20 - 2014-09-22 - 2014-10-05",
"endDate": "2014-10-05",
"id": "2014BiW20",
"iso": "2014BiW20",
"name": "Bi-Week 20 - 2014-09-22 - 2014-10-05",
+ "periodType": "BIWEEKLY",
"startDate": "2014-09-22",
},
Object {
+ "displayName": "Bi-Week 21 - 2014-10-06 - 2014-10-19",
"endDate": "2014-10-19",
"id": "2014BiW21",
"iso": "2014BiW21",
"name": "Bi-Week 21 - 2014-10-06 - 2014-10-19",
+ "periodType": "BIWEEKLY",
"startDate": "2014-10-06",
},
Object {
+ "displayName": "Bi-Week 22 - 2014-10-20 - 2014-11-02",
"endDate": "2014-11-02",
"id": "2014BiW22",
"iso": "2014BiW22",
"name": "Bi-Week 22 - 2014-10-20 - 2014-11-02",
+ "periodType": "BIWEEKLY",
"startDate": "2014-10-20",
},
Object {
+ "displayName": "Bi-Week 23 - 2014-11-03 - 2014-11-16",
"endDate": "2014-11-16",
"id": "2014BiW23",
"iso": "2014BiW23",
"name": "Bi-Week 23 - 2014-11-03 - 2014-11-16",
+ "periodType": "BIWEEKLY",
"startDate": "2014-11-03",
},
Object {
+ "displayName": "Bi-Week 24 - 2014-11-17 - 2014-11-30",
"endDate": "2014-11-30",
"id": "2014BiW24",
"iso": "2014BiW24",
"name": "Bi-Week 24 - 2014-11-17 - 2014-11-30",
+ "periodType": "BIWEEKLY",
"startDate": "2014-11-17",
},
Object {
+ "displayName": "Bi-Week 25 - 2014-12-01 - 2014-12-14",
"endDate": "2014-12-14",
"id": "2014BiW25",
"iso": "2014BiW25",
"name": "Bi-Week 25 - 2014-12-01 - 2014-12-14",
+ "periodType": "BIWEEKLY",
"startDate": "2014-12-01",
},
Object {
+ "displayName": "Bi-Week 26 - 2014-12-15 - 2014-12-28",
"endDate": "2014-12-28",
"id": "2014BiW26",
"iso": "2014BiW26",
"name": "Bi-Week 26 - 2014-12-15 - 2014-12-28",
+ "periodType": "BIWEEKLY",
"startDate": "2014-12-15",
},
],
@@ -198,45 +250,57 @@ Object {
"name": "Bi-monthly",
"options": Array [
Object {
+ "displayName": "January - February 2014",
"endDate": "2014-02-28",
"id": "201401B",
"iso": "201401B",
"name": "January - February 2014",
+ "periodType": "BIMONTHLY",
"startDate": "2014-01-01",
},
Object {
+ "displayName": "March - April 2014",
"endDate": "2014-04-30",
"id": "201402B",
"iso": "201402B",
"name": "March - April 2014",
+ "periodType": "BIMONTHLY",
"startDate": "2014-03-01",
},
Object {
+ "displayName": "May - June 2014",
"endDate": "2014-06-30",
"id": "201403B",
"iso": "201403B",
"name": "May - June 2014",
+ "periodType": "BIMONTHLY",
"startDate": "2014-05-01",
},
Object {
+ "displayName": "July - August 2014",
"endDate": "2014-08-31",
"id": "201404B",
"iso": "201404B",
"name": "July - August 2014",
+ "periodType": "BIMONTHLY",
"startDate": "2014-07-01",
},
Object {
+ "displayName": "September - October 2014",
"endDate": "2014-10-31",
"id": "201405B",
"iso": "201405B",
"name": "September - October 2014",
+ "periodType": "BIMONTHLY",
"startDate": "2014-09-01",
},
Object {
+ "displayName": "November - December 2014",
"endDate": "2014-12-31",
"id": "201406B",
"iso": "201406B",
"name": "November - December 2014",
+ "periodType": "BIMONTHLY",
"startDate": "2014-11-01",
},
],
@@ -250,2558 +314,3288 @@ Object {
"name": "Daily",
"options": Array [
Object {
+ "displayName": "January 1, 2014",
"endDate": "2014-01-01",
"id": "20140101",
"iso": "20140101",
"name": "2014-01-01",
+ "periodType": "DAILY",
"startDate": "2014-01-01",
},
Object {
+ "displayName": "January 2, 2014",
"endDate": "2014-01-02",
"id": "20140102",
"iso": "20140102",
"name": "2014-01-02",
+ "periodType": "DAILY",
"startDate": "2014-01-02",
},
Object {
+ "displayName": "January 3, 2014",
"endDate": "2014-01-03",
"id": "20140103",
"iso": "20140103",
"name": "2014-01-03",
+ "periodType": "DAILY",
"startDate": "2014-01-03",
},
Object {
+ "displayName": "January 4, 2014",
"endDate": "2014-01-04",
"id": "20140104",
"iso": "20140104",
"name": "2014-01-04",
+ "periodType": "DAILY",
"startDate": "2014-01-04",
},
Object {
+ "displayName": "January 5, 2014",
"endDate": "2014-01-05",
"id": "20140105",
"iso": "20140105",
"name": "2014-01-05",
+ "periodType": "DAILY",
"startDate": "2014-01-05",
},
Object {
+ "displayName": "January 6, 2014",
"endDate": "2014-01-06",
"id": "20140106",
"iso": "20140106",
"name": "2014-01-06",
+ "periodType": "DAILY",
"startDate": "2014-01-06",
},
Object {
+ "displayName": "January 7, 2014",
"endDate": "2014-01-07",
"id": "20140107",
"iso": "20140107",
"name": "2014-01-07",
+ "periodType": "DAILY",
"startDate": "2014-01-07",
},
Object {
+ "displayName": "January 8, 2014",
"endDate": "2014-01-08",
"id": "20140108",
"iso": "20140108",
"name": "2014-01-08",
+ "periodType": "DAILY",
"startDate": "2014-01-08",
},
Object {
+ "displayName": "January 9, 2014",
"endDate": "2014-01-09",
"id": "20140109",
"iso": "20140109",
"name": "2014-01-09",
+ "periodType": "DAILY",
"startDate": "2014-01-09",
},
Object {
+ "displayName": "January 10, 2014",
"endDate": "2014-01-10",
"id": "20140110",
"iso": "20140110",
"name": "2014-01-10",
+ "periodType": "DAILY",
"startDate": "2014-01-10",
},
Object {
+ "displayName": "January 11, 2014",
"endDate": "2014-01-11",
"id": "20140111",
"iso": "20140111",
"name": "2014-01-11",
+ "periodType": "DAILY",
"startDate": "2014-01-11",
},
Object {
+ "displayName": "January 12, 2014",
"endDate": "2014-01-12",
"id": "20140112",
"iso": "20140112",
"name": "2014-01-12",
+ "periodType": "DAILY",
"startDate": "2014-01-12",
},
Object {
+ "displayName": "January 13, 2014",
"endDate": "2014-01-13",
"id": "20140113",
"iso": "20140113",
"name": "2014-01-13",
+ "periodType": "DAILY",
"startDate": "2014-01-13",
},
Object {
+ "displayName": "January 14, 2014",
"endDate": "2014-01-14",
"id": "20140114",
"iso": "20140114",
"name": "2014-01-14",
+ "periodType": "DAILY",
"startDate": "2014-01-14",
},
Object {
+ "displayName": "January 15, 2014",
"endDate": "2014-01-15",
"id": "20140115",
"iso": "20140115",
"name": "2014-01-15",
+ "periodType": "DAILY",
"startDate": "2014-01-15",
},
Object {
+ "displayName": "January 16, 2014",
"endDate": "2014-01-16",
"id": "20140116",
"iso": "20140116",
"name": "2014-01-16",
+ "periodType": "DAILY",
"startDate": "2014-01-16",
},
Object {
+ "displayName": "January 17, 2014",
"endDate": "2014-01-17",
"id": "20140117",
"iso": "20140117",
"name": "2014-01-17",
+ "periodType": "DAILY",
"startDate": "2014-01-17",
},
Object {
+ "displayName": "January 18, 2014",
"endDate": "2014-01-18",
"id": "20140118",
"iso": "20140118",
"name": "2014-01-18",
+ "periodType": "DAILY",
"startDate": "2014-01-18",
},
Object {
+ "displayName": "January 19, 2014",
"endDate": "2014-01-19",
"id": "20140119",
"iso": "20140119",
"name": "2014-01-19",
+ "periodType": "DAILY",
"startDate": "2014-01-19",
},
Object {
+ "displayName": "January 20, 2014",
"endDate": "2014-01-20",
"id": "20140120",
"iso": "20140120",
"name": "2014-01-20",
+ "periodType": "DAILY",
"startDate": "2014-01-20",
},
Object {
+ "displayName": "January 21, 2014",
"endDate": "2014-01-21",
"id": "20140121",
"iso": "20140121",
"name": "2014-01-21",
+ "periodType": "DAILY",
"startDate": "2014-01-21",
},
Object {
+ "displayName": "January 22, 2014",
"endDate": "2014-01-22",
"id": "20140122",
"iso": "20140122",
"name": "2014-01-22",
+ "periodType": "DAILY",
"startDate": "2014-01-22",
},
Object {
+ "displayName": "January 23, 2014",
"endDate": "2014-01-23",
"id": "20140123",
"iso": "20140123",
"name": "2014-01-23",
+ "periodType": "DAILY",
"startDate": "2014-01-23",
},
Object {
+ "displayName": "January 24, 2014",
"endDate": "2014-01-24",
"id": "20140124",
"iso": "20140124",
"name": "2014-01-24",
+ "periodType": "DAILY",
"startDate": "2014-01-24",
},
Object {
+ "displayName": "January 25, 2014",
"endDate": "2014-01-25",
"id": "20140125",
"iso": "20140125",
"name": "2014-01-25",
+ "periodType": "DAILY",
"startDate": "2014-01-25",
},
Object {
+ "displayName": "January 26, 2014",
"endDate": "2014-01-26",
"id": "20140126",
"iso": "20140126",
"name": "2014-01-26",
+ "periodType": "DAILY",
"startDate": "2014-01-26",
},
Object {
+ "displayName": "January 27, 2014",
"endDate": "2014-01-27",
"id": "20140127",
"iso": "20140127",
"name": "2014-01-27",
+ "periodType": "DAILY",
"startDate": "2014-01-27",
},
Object {
+ "displayName": "January 28, 2014",
"endDate": "2014-01-28",
"id": "20140128",
"iso": "20140128",
"name": "2014-01-28",
+ "periodType": "DAILY",
"startDate": "2014-01-28",
},
Object {
+ "displayName": "January 29, 2014",
"endDate": "2014-01-29",
"id": "20140129",
"iso": "20140129",
"name": "2014-01-29",
+ "periodType": "DAILY",
"startDate": "2014-01-29",
},
Object {
+ "displayName": "January 30, 2014",
"endDate": "2014-01-30",
"id": "20140130",
"iso": "20140130",
"name": "2014-01-30",
+ "periodType": "DAILY",
"startDate": "2014-01-30",
},
Object {
+ "displayName": "January 31, 2014",
"endDate": "2014-01-31",
"id": "20140131",
"iso": "20140131",
"name": "2014-01-31",
+ "periodType": "DAILY",
"startDate": "2014-01-31",
},
Object {
+ "displayName": "February 1, 2014",
"endDate": "2014-02-01",
"id": "20140201",
"iso": "20140201",
"name": "2014-02-01",
+ "periodType": "DAILY",
"startDate": "2014-02-01",
},
Object {
+ "displayName": "February 2, 2014",
"endDate": "2014-02-02",
"id": "20140202",
"iso": "20140202",
"name": "2014-02-02",
+ "periodType": "DAILY",
"startDate": "2014-02-02",
},
Object {
+ "displayName": "February 3, 2014",
"endDate": "2014-02-03",
"id": "20140203",
"iso": "20140203",
"name": "2014-02-03",
+ "periodType": "DAILY",
"startDate": "2014-02-03",
},
Object {
+ "displayName": "February 4, 2014",
"endDate": "2014-02-04",
"id": "20140204",
"iso": "20140204",
"name": "2014-02-04",
+ "periodType": "DAILY",
"startDate": "2014-02-04",
},
Object {
+ "displayName": "February 5, 2014",
"endDate": "2014-02-05",
"id": "20140205",
"iso": "20140205",
"name": "2014-02-05",
+ "periodType": "DAILY",
"startDate": "2014-02-05",
},
Object {
+ "displayName": "February 6, 2014",
"endDate": "2014-02-06",
"id": "20140206",
"iso": "20140206",
"name": "2014-02-06",
+ "periodType": "DAILY",
"startDate": "2014-02-06",
},
Object {
+ "displayName": "February 7, 2014",
"endDate": "2014-02-07",
"id": "20140207",
"iso": "20140207",
"name": "2014-02-07",
+ "periodType": "DAILY",
"startDate": "2014-02-07",
},
Object {
+ "displayName": "February 8, 2014",
"endDate": "2014-02-08",
"id": "20140208",
"iso": "20140208",
"name": "2014-02-08",
+ "periodType": "DAILY",
"startDate": "2014-02-08",
},
Object {
+ "displayName": "February 9, 2014",
"endDate": "2014-02-09",
"id": "20140209",
"iso": "20140209",
"name": "2014-02-09",
+ "periodType": "DAILY",
"startDate": "2014-02-09",
},
Object {
+ "displayName": "February 10, 2014",
"endDate": "2014-02-10",
"id": "20140210",
"iso": "20140210",
"name": "2014-02-10",
+ "periodType": "DAILY",
"startDate": "2014-02-10",
},
Object {
+ "displayName": "February 11, 2014",
"endDate": "2014-02-11",
"id": "20140211",
"iso": "20140211",
"name": "2014-02-11",
+ "periodType": "DAILY",
"startDate": "2014-02-11",
},
Object {
+ "displayName": "February 12, 2014",
"endDate": "2014-02-12",
"id": "20140212",
"iso": "20140212",
"name": "2014-02-12",
+ "periodType": "DAILY",
"startDate": "2014-02-12",
},
Object {
+ "displayName": "February 13, 2014",
"endDate": "2014-02-13",
"id": "20140213",
"iso": "20140213",
"name": "2014-02-13",
+ "periodType": "DAILY",
"startDate": "2014-02-13",
},
Object {
+ "displayName": "February 14, 2014",
"endDate": "2014-02-14",
"id": "20140214",
"iso": "20140214",
"name": "2014-02-14",
+ "periodType": "DAILY",
"startDate": "2014-02-14",
},
Object {
+ "displayName": "February 15, 2014",
"endDate": "2014-02-15",
"id": "20140215",
"iso": "20140215",
"name": "2014-02-15",
+ "periodType": "DAILY",
"startDate": "2014-02-15",
},
Object {
+ "displayName": "February 16, 2014",
"endDate": "2014-02-16",
"id": "20140216",
"iso": "20140216",
"name": "2014-02-16",
+ "periodType": "DAILY",
"startDate": "2014-02-16",
},
Object {
+ "displayName": "February 17, 2014",
"endDate": "2014-02-17",
"id": "20140217",
"iso": "20140217",
"name": "2014-02-17",
+ "periodType": "DAILY",
"startDate": "2014-02-17",
},
Object {
+ "displayName": "February 18, 2014",
"endDate": "2014-02-18",
"id": "20140218",
"iso": "20140218",
"name": "2014-02-18",
+ "periodType": "DAILY",
"startDate": "2014-02-18",
},
Object {
+ "displayName": "February 19, 2014",
"endDate": "2014-02-19",
"id": "20140219",
"iso": "20140219",
"name": "2014-02-19",
+ "periodType": "DAILY",
"startDate": "2014-02-19",
},
Object {
+ "displayName": "February 20, 2014",
"endDate": "2014-02-20",
"id": "20140220",
"iso": "20140220",
"name": "2014-02-20",
+ "periodType": "DAILY",
"startDate": "2014-02-20",
},
Object {
+ "displayName": "February 21, 2014",
"endDate": "2014-02-21",
"id": "20140221",
"iso": "20140221",
"name": "2014-02-21",
+ "periodType": "DAILY",
"startDate": "2014-02-21",
},
Object {
+ "displayName": "February 22, 2014",
"endDate": "2014-02-22",
"id": "20140222",
"iso": "20140222",
"name": "2014-02-22",
+ "periodType": "DAILY",
"startDate": "2014-02-22",
},
Object {
+ "displayName": "February 23, 2014",
"endDate": "2014-02-23",
"id": "20140223",
"iso": "20140223",
"name": "2014-02-23",
+ "periodType": "DAILY",
"startDate": "2014-02-23",
},
Object {
+ "displayName": "February 24, 2014",
"endDate": "2014-02-24",
"id": "20140224",
"iso": "20140224",
"name": "2014-02-24",
+ "periodType": "DAILY",
"startDate": "2014-02-24",
},
Object {
+ "displayName": "February 25, 2014",
"endDate": "2014-02-25",
"id": "20140225",
"iso": "20140225",
"name": "2014-02-25",
+ "periodType": "DAILY",
"startDate": "2014-02-25",
},
Object {
+ "displayName": "February 26, 2014",
"endDate": "2014-02-26",
"id": "20140226",
"iso": "20140226",
"name": "2014-02-26",
+ "periodType": "DAILY",
"startDate": "2014-02-26",
},
Object {
+ "displayName": "February 27, 2014",
"endDate": "2014-02-27",
"id": "20140227",
"iso": "20140227",
"name": "2014-02-27",
+ "periodType": "DAILY",
"startDate": "2014-02-27",
},
Object {
+ "displayName": "February 28, 2014",
"endDate": "2014-02-28",
"id": "20140228",
"iso": "20140228",
"name": "2014-02-28",
+ "periodType": "DAILY",
"startDate": "2014-02-28",
},
Object {
+ "displayName": "March 1, 2014",
"endDate": "2014-03-01",
"id": "20140301",
"iso": "20140301",
"name": "2014-03-01",
+ "periodType": "DAILY",
"startDate": "2014-03-01",
},
Object {
+ "displayName": "March 2, 2014",
"endDate": "2014-03-02",
"id": "20140302",
"iso": "20140302",
"name": "2014-03-02",
+ "periodType": "DAILY",
"startDate": "2014-03-02",
},
Object {
+ "displayName": "March 3, 2014",
"endDate": "2014-03-03",
"id": "20140303",
"iso": "20140303",
"name": "2014-03-03",
+ "periodType": "DAILY",
"startDate": "2014-03-03",
},
Object {
+ "displayName": "March 4, 2014",
"endDate": "2014-03-04",
"id": "20140304",
"iso": "20140304",
"name": "2014-03-04",
+ "periodType": "DAILY",
"startDate": "2014-03-04",
},
Object {
+ "displayName": "March 5, 2014",
"endDate": "2014-03-05",
"id": "20140305",
"iso": "20140305",
"name": "2014-03-05",
+ "periodType": "DAILY",
"startDate": "2014-03-05",
},
Object {
+ "displayName": "March 6, 2014",
"endDate": "2014-03-06",
"id": "20140306",
"iso": "20140306",
"name": "2014-03-06",
+ "periodType": "DAILY",
"startDate": "2014-03-06",
},
Object {
+ "displayName": "March 7, 2014",
"endDate": "2014-03-07",
"id": "20140307",
"iso": "20140307",
"name": "2014-03-07",
+ "periodType": "DAILY",
"startDate": "2014-03-07",
},
Object {
+ "displayName": "March 8, 2014",
"endDate": "2014-03-08",
"id": "20140308",
"iso": "20140308",
"name": "2014-03-08",
+ "periodType": "DAILY",
"startDate": "2014-03-08",
},
Object {
+ "displayName": "March 9, 2014",
"endDate": "2014-03-09",
"id": "20140309",
"iso": "20140309",
"name": "2014-03-09",
+ "periodType": "DAILY",
"startDate": "2014-03-09",
},
Object {
+ "displayName": "March 10, 2014",
"endDate": "2014-03-10",
"id": "20140310",
"iso": "20140310",
"name": "2014-03-10",
+ "periodType": "DAILY",
"startDate": "2014-03-10",
},
Object {
+ "displayName": "March 11, 2014",
"endDate": "2014-03-11",
"id": "20140311",
"iso": "20140311",
"name": "2014-03-11",
+ "periodType": "DAILY",
"startDate": "2014-03-11",
},
Object {
+ "displayName": "March 12, 2014",
"endDate": "2014-03-12",
"id": "20140312",
"iso": "20140312",
"name": "2014-03-12",
+ "periodType": "DAILY",
"startDate": "2014-03-12",
},
Object {
+ "displayName": "March 13, 2014",
"endDate": "2014-03-13",
"id": "20140313",
"iso": "20140313",
"name": "2014-03-13",
+ "periodType": "DAILY",
"startDate": "2014-03-13",
},
Object {
+ "displayName": "March 14, 2014",
"endDate": "2014-03-14",
"id": "20140314",
"iso": "20140314",
"name": "2014-03-14",
+ "periodType": "DAILY",
"startDate": "2014-03-14",
},
Object {
+ "displayName": "March 15, 2014",
"endDate": "2014-03-15",
"id": "20140315",
"iso": "20140315",
"name": "2014-03-15",
+ "periodType": "DAILY",
"startDate": "2014-03-15",
},
Object {
+ "displayName": "March 16, 2014",
"endDate": "2014-03-16",
"id": "20140316",
"iso": "20140316",
"name": "2014-03-16",
+ "periodType": "DAILY",
"startDate": "2014-03-16",
},
Object {
+ "displayName": "March 17, 2014",
"endDate": "2014-03-17",
"id": "20140317",
"iso": "20140317",
"name": "2014-03-17",
+ "periodType": "DAILY",
"startDate": "2014-03-17",
},
Object {
+ "displayName": "March 18, 2014",
"endDate": "2014-03-18",
"id": "20140318",
"iso": "20140318",
"name": "2014-03-18",
+ "periodType": "DAILY",
"startDate": "2014-03-18",
},
Object {
+ "displayName": "March 19, 2014",
"endDate": "2014-03-19",
"id": "20140319",
"iso": "20140319",
"name": "2014-03-19",
+ "periodType": "DAILY",
"startDate": "2014-03-19",
},
Object {
+ "displayName": "March 20, 2014",
"endDate": "2014-03-20",
"id": "20140320",
"iso": "20140320",
"name": "2014-03-20",
+ "periodType": "DAILY",
"startDate": "2014-03-20",
},
Object {
+ "displayName": "March 21, 2014",
"endDate": "2014-03-21",
"id": "20140321",
"iso": "20140321",
"name": "2014-03-21",
+ "periodType": "DAILY",
"startDate": "2014-03-21",
},
Object {
+ "displayName": "March 22, 2014",
"endDate": "2014-03-22",
"id": "20140322",
"iso": "20140322",
"name": "2014-03-22",
+ "periodType": "DAILY",
"startDate": "2014-03-22",
},
Object {
+ "displayName": "March 23, 2014",
"endDate": "2014-03-23",
"id": "20140323",
"iso": "20140323",
"name": "2014-03-23",
+ "periodType": "DAILY",
"startDate": "2014-03-23",
},
Object {
+ "displayName": "March 24, 2014",
"endDate": "2014-03-24",
"id": "20140324",
"iso": "20140324",
"name": "2014-03-24",
+ "periodType": "DAILY",
"startDate": "2014-03-24",
},
Object {
+ "displayName": "March 25, 2014",
"endDate": "2014-03-25",
"id": "20140325",
"iso": "20140325",
"name": "2014-03-25",
+ "periodType": "DAILY",
"startDate": "2014-03-25",
},
Object {
+ "displayName": "March 26, 2014",
"endDate": "2014-03-26",
"id": "20140326",
"iso": "20140326",
"name": "2014-03-26",
+ "periodType": "DAILY",
"startDate": "2014-03-26",
},
Object {
+ "displayName": "March 27, 2014",
"endDate": "2014-03-27",
"id": "20140327",
"iso": "20140327",
"name": "2014-03-27",
+ "periodType": "DAILY",
"startDate": "2014-03-27",
},
Object {
+ "displayName": "March 28, 2014",
"endDate": "2014-03-28",
"id": "20140328",
"iso": "20140328",
"name": "2014-03-28",
+ "periodType": "DAILY",
"startDate": "2014-03-28",
},
Object {
+ "displayName": "March 29, 2014",
"endDate": "2014-03-29",
"id": "20140329",
"iso": "20140329",
"name": "2014-03-29",
+ "periodType": "DAILY",
"startDate": "2014-03-29",
},
Object {
+ "displayName": "March 30, 2014",
"endDate": "2014-03-30",
"id": "20140330",
"iso": "20140330",
"name": "2014-03-30",
+ "periodType": "DAILY",
"startDate": "2014-03-30",
},
Object {
+ "displayName": "March 31, 2014",
"endDate": "2014-03-31",
"id": "20140331",
"iso": "20140331",
"name": "2014-03-31",
+ "periodType": "DAILY",
"startDate": "2014-03-31",
},
Object {
+ "displayName": "April 1, 2014",
"endDate": "2014-04-01",
"id": "20140401",
"iso": "20140401",
"name": "2014-04-01",
+ "periodType": "DAILY",
"startDate": "2014-04-01",
},
Object {
+ "displayName": "April 2, 2014",
"endDate": "2014-04-02",
"id": "20140402",
"iso": "20140402",
"name": "2014-04-02",
+ "periodType": "DAILY",
"startDate": "2014-04-02",
},
Object {
+ "displayName": "April 3, 2014",
"endDate": "2014-04-03",
"id": "20140403",
"iso": "20140403",
"name": "2014-04-03",
+ "periodType": "DAILY",
"startDate": "2014-04-03",
},
Object {
+ "displayName": "April 4, 2014",
"endDate": "2014-04-04",
"id": "20140404",
"iso": "20140404",
"name": "2014-04-04",
+ "periodType": "DAILY",
"startDate": "2014-04-04",
},
Object {
+ "displayName": "April 5, 2014",
"endDate": "2014-04-05",
"id": "20140405",
"iso": "20140405",
"name": "2014-04-05",
+ "periodType": "DAILY",
"startDate": "2014-04-05",
},
Object {
+ "displayName": "April 6, 2014",
"endDate": "2014-04-06",
"id": "20140406",
"iso": "20140406",
"name": "2014-04-06",
+ "periodType": "DAILY",
"startDate": "2014-04-06",
},
Object {
+ "displayName": "April 7, 2014",
"endDate": "2014-04-07",
"id": "20140407",
"iso": "20140407",
"name": "2014-04-07",
+ "periodType": "DAILY",
"startDate": "2014-04-07",
},
Object {
+ "displayName": "April 8, 2014",
"endDate": "2014-04-08",
"id": "20140408",
"iso": "20140408",
"name": "2014-04-08",
+ "periodType": "DAILY",
"startDate": "2014-04-08",
},
Object {
+ "displayName": "April 9, 2014",
"endDate": "2014-04-09",
"id": "20140409",
"iso": "20140409",
"name": "2014-04-09",
+ "periodType": "DAILY",
"startDate": "2014-04-09",
},
Object {
+ "displayName": "April 10, 2014",
"endDate": "2014-04-10",
"id": "20140410",
"iso": "20140410",
"name": "2014-04-10",
+ "periodType": "DAILY",
"startDate": "2014-04-10",
},
Object {
+ "displayName": "April 11, 2014",
"endDate": "2014-04-11",
"id": "20140411",
"iso": "20140411",
"name": "2014-04-11",
+ "periodType": "DAILY",
"startDate": "2014-04-11",
},
Object {
+ "displayName": "April 12, 2014",
"endDate": "2014-04-12",
"id": "20140412",
"iso": "20140412",
"name": "2014-04-12",
+ "periodType": "DAILY",
"startDate": "2014-04-12",
},
Object {
+ "displayName": "April 13, 2014",
"endDate": "2014-04-13",
"id": "20140413",
"iso": "20140413",
"name": "2014-04-13",
+ "periodType": "DAILY",
"startDate": "2014-04-13",
},
Object {
+ "displayName": "April 14, 2014",
"endDate": "2014-04-14",
"id": "20140414",
"iso": "20140414",
"name": "2014-04-14",
+ "periodType": "DAILY",
"startDate": "2014-04-14",
},
Object {
+ "displayName": "April 15, 2014",
"endDate": "2014-04-15",
"id": "20140415",
"iso": "20140415",
"name": "2014-04-15",
+ "periodType": "DAILY",
"startDate": "2014-04-15",
},
Object {
+ "displayName": "April 16, 2014",
"endDate": "2014-04-16",
"id": "20140416",
"iso": "20140416",
"name": "2014-04-16",
+ "periodType": "DAILY",
"startDate": "2014-04-16",
},
Object {
+ "displayName": "April 17, 2014",
"endDate": "2014-04-17",
"id": "20140417",
"iso": "20140417",
"name": "2014-04-17",
+ "periodType": "DAILY",
"startDate": "2014-04-17",
},
Object {
+ "displayName": "April 18, 2014",
"endDate": "2014-04-18",
"id": "20140418",
"iso": "20140418",
"name": "2014-04-18",
+ "periodType": "DAILY",
"startDate": "2014-04-18",
},
Object {
+ "displayName": "April 19, 2014",
"endDate": "2014-04-19",
"id": "20140419",
"iso": "20140419",
"name": "2014-04-19",
+ "periodType": "DAILY",
"startDate": "2014-04-19",
},
Object {
+ "displayName": "April 20, 2014",
"endDate": "2014-04-20",
"id": "20140420",
"iso": "20140420",
"name": "2014-04-20",
+ "periodType": "DAILY",
"startDate": "2014-04-20",
},
Object {
+ "displayName": "April 21, 2014",
"endDate": "2014-04-21",
"id": "20140421",
"iso": "20140421",
"name": "2014-04-21",
+ "periodType": "DAILY",
"startDate": "2014-04-21",
},
Object {
+ "displayName": "April 22, 2014",
"endDate": "2014-04-22",
"id": "20140422",
"iso": "20140422",
"name": "2014-04-22",
+ "periodType": "DAILY",
"startDate": "2014-04-22",
},
Object {
+ "displayName": "April 23, 2014",
"endDate": "2014-04-23",
"id": "20140423",
"iso": "20140423",
"name": "2014-04-23",
+ "periodType": "DAILY",
"startDate": "2014-04-23",
},
Object {
+ "displayName": "April 24, 2014",
"endDate": "2014-04-24",
"id": "20140424",
"iso": "20140424",
"name": "2014-04-24",
+ "periodType": "DAILY",
"startDate": "2014-04-24",
},
Object {
+ "displayName": "April 25, 2014",
"endDate": "2014-04-25",
"id": "20140425",
"iso": "20140425",
"name": "2014-04-25",
+ "periodType": "DAILY",
"startDate": "2014-04-25",
},
Object {
+ "displayName": "April 26, 2014",
"endDate": "2014-04-26",
"id": "20140426",
"iso": "20140426",
"name": "2014-04-26",
+ "periodType": "DAILY",
"startDate": "2014-04-26",
},
Object {
+ "displayName": "April 27, 2014",
"endDate": "2014-04-27",
"id": "20140427",
"iso": "20140427",
"name": "2014-04-27",
+ "periodType": "DAILY",
"startDate": "2014-04-27",
},
Object {
+ "displayName": "April 28, 2014",
"endDate": "2014-04-28",
"id": "20140428",
"iso": "20140428",
"name": "2014-04-28",
+ "periodType": "DAILY",
"startDate": "2014-04-28",
},
Object {
+ "displayName": "April 29, 2014",
"endDate": "2014-04-29",
"id": "20140429",
"iso": "20140429",
"name": "2014-04-29",
+ "periodType": "DAILY",
"startDate": "2014-04-29",
},
Object {
+ "displayName": "April 30, 2014",
"endDate": "2014-04-30",
"id": "20140430",
"iso": "20140430",
"name": "2014-04-30",
+ "periodType": "DAILY",
"startDate": "2014-04-30",
},
Object {
+ "displayName": "May 1, 2014",
"endDate": "2014-05-01",
"id": "20140501",
"iso": "20140501",
"name": "2014-05-01",
+ "periodType": "DAILY",
"startDate": "2014-05-01",
},
Object {
+ "displayName": "May 2, 2014",
"endDate": "2014-05-02",
"id": "20140502",
"iso": "20140502",
"name": "2014-05-02",
+ "periodType": "DAILY",
"startDate": "2014-05-02",
},
Object {
+ "displayName": "May 3, 2014",
"endDate": "2014-05-03",
"id": "20140503",
"iso": "20140503",
"name": "2014-05-03",
+ "periodType": "DAILY",
"startDate": "2014-05-03",
},
Object {
+ "displayName": "May 4, 2014",
"endDate": "2014-05-04",
"id": "20140504",
"iso": "20140504",
"name": "2014-05-04",
+ "periodType": "DAILY",
"startDate": "2014-05-04",
},
Object {
+ "displayName": "May 5, 2014",
"endDate": "2014-05-05",
"id": "20140505",
"iso": "20140505",
"name": "2014-05-05",
+ "periodType": "DAILY",
"startDate": "2014-05-05",
},
Object {
+ "displayName": "May 6, 2014",
"endDate": "2014-05-06",
"id": "20140506",
"iso": "20140506",
"name": "2014-05-06",
+ "periodType": "DAILY",
"startDate": "2014-05-06",
},
Object {
+ "displayName": "May 7, 2014",
"endDate": "2014-05-07",
"id": "20140507",
"iso": "20140507",
"name": "2014-05-07",
+ "periodType": "DAILY",
"startDate": "2014-05-07",
},
Object {
+ "displayName": "May 8, 2014",
"endDate": "2014-05-08",
"id": "20140508",
"iso": "20140508",
"name": "2014-05-08",
+ "periodType": "DAILY",
"startDate": "2014-05-08",
},
Object {
+ "displayName": "May 9, 2014",
"endDate": "2014-05-09",
"id": "20140509",
"iso": "20140509",
"name": "2014-05-09",
+ "periodType": "DAILY",
"startDate": "2014-05-09",
},
Object {
+ "displayName": "May 10, 2014",
"endDate": "2014-05-10",
"id": "20140510",
"iso": "20140510",
"name": "2014-05-10",
+ "periodType": "DAILY",
"startDate": "2014-05-10",
},
Object {
+ "displayName": "May 11, 2014",
"endDate": "2014-05-11",
"id": "20140511",
"iso": "20140511",
"name": "2014-05-11",
+ "periodType": "DAILY",
"startDate": "2014-05-11",
},
Object {
+ "displayName": "May 12, 2014",
"endDate": "2014-05-12",
"id": "20140512",
"iso": "20140512",
"name": "2014-05-12",
+ "periodType": "DAILY",
"startDate": "2014-05-12",
},
Object {
+ "displayName": "May 13, 2014",
"endDate": "2014-05-13",
"id": "20140513",
"iso": "20140513",
"name": "2014-05-13",
+ "periodType": "DAILY",
"startDate": "2014-05-13",
},
Object {
+ "displayName": "May 14, 2014",
"endDate": "2014-05-14",
"id": "20140514",
"iso": "20140514",
"name": "2014-05-14",
+ "periodType": "DAILY",
"startDate": "2014-05-14",
},
Object {
+ "displayName": "May 15, 2014",
"endDate": "2014-05-15",
"id": "20140515",
"iso": "20140515",
"name": "2014-05-15",
+ "periodType": "DAILY",
"startDate": "2014-05-15",
},
Object {
+ "displayName": "May 16, 2014",
"endDate": "2014-05-16",
"id": "20140516",
"iso": "20140516",
"name": "2014-05-16",
+ "periodType": "DAILY",
"startDate": "2014-05-16",
},
Object {
+ "displayName": "May 17, 2014",
"endDate": "2014-05-17",
"id": "20140517",
"iso": "20140517",
"name": "2014-05-17",
+ "periodType": "DAILY",
"startDate": "2014-05-17",
},
Object {
+ "displayName": "May 18, 2014",
"endDate": "2014-05-18",
"id": "20140518",
"iso": "20140518",
"name": "2014-05-18",
+ "periodType": "DAILY",
"startDate": "2014-05-18",
},
Object {
+ "displayName": "May 19, 2014",
"endDate": "2014-05-19",
"id": "20140519",
"iso": "20140519",
"name": "2014-05-19",
+ "periodType": "DAILY",
"startDate": "2014-05-19",
},
Object {
+ "displayName": "May 20, 2014",
"endDate": "2014-05-20",
"id": "20140520",
"iso": "20140520",
"name": "2014-05-20",
+ "periodType": "DAILY",
"startDate": "2014-05-20",
},
Object {
+ "displayName": "May 21, 2014",
"endDate": "2014-05-21",
"id": "20140521",
"iso": "20140521",
"name": "2014-05-21",
+ "periodType": "DAILY",
"startDate": "2014-05-21",
},
Object {
+ "displayName": "May 22, 2014",
"endDate": "2014-05-22",
"id": "20140522",
"iso": "20140522",
"name": "2014-05-22",
+ "periodType": "DAILY",
"startDate": "2014-05-22",
},
Object {
+ "displayName": "May 23, 2014",
"endDate": "2014-05-23",
"id": "20140523",
"iso": "20140523",
"name": "2014-05-23",
+ "periodType": "DAILY",
"startDate": "2014-05-23",
},
Object {
+ "displayName": "May 24, 2014",
"endDate": "2014-05-24",
"id": "20140524",
"iso": "20140524",
"name": "2014-05-24",
+ "periodType": "DAILY",
"startDate": "2014-05-24",
},
Object {
+ "displayName": "May 25, 2014",
"endDate": "2014-05-25",
"id": "20140525",
"iso": "20140525",
"name": "2014-05-25",
+ "periodType": "DAILY",
"startDate": "2014-05-25",
},
Object {
+ "displayName": "May 26, 2014",
"endDate": "2014-05-26",
"id": "20140526",
"iso": "20140526",
"name": "2014-05-26",
+ "periodType": "DAILY",
"startDate": "2014-05-26",
},
Object {
+ "displayName": "May 27, 2014",
"endDate": "2014-05-27",
"id": "20140527",
"iso": "20140527",
"name": "2014-05-27",
+ "periodType": "DAILY",
"startDate": "2014-05-27",
},
Object {
+ "displayName": "May 28, 2014",
"endDate": "2014-05-28",
"id": "20140528",
"iso": "20140528",
"name": "2014-05-28",
+ "periodType": "DAILY",
"startDate": "2014-05-28",
},
Object {
+ "displayName": "May 29, 2014",
"endDate": "2014-05-29",
"id": "20140529",
"iso": "20140529",
"name": "2014-05-29",
+ "periodType": "DAILY",
"startDate": "2014-05-29",
},
Object {
+ "displayName": "May 30, 2014",
"endDate": "2014-05-30",
"id": "20140530",
"iso": "20140530",
"name": "2014-05-30",
+ "periodType": "DAILY",
"startDate": "2014-05-30",
},
Object {
+ "displayName": "May 31, 2014",
"endDate": "2014-05-31",
"id": "20140531",
"iso": "20140531",
"name": "2014-05-31",
+ "periodType": "DAILY",
"startDate": "2014-05-31",
},
Object {
+ "displayName": "June 1, 2014",
"endDate": "2014-06-01",
"id": "20140601",
"iso": "20140601",
"name": "2014-06-01",
+ "periodType": "DAILY",
"startDate": "2014-06-01",
},
Object {
+ "displayName": "June 2, 2014",
"endDate": "2014-06-02",
"id": "20140602",
"iso": "20140602",
"name": "2014-06-02",
+ "periodType": "DAILY",
"startDate": "2014-06-02",
},
Object {
+ "displayName": "June 3, 2014",
"endDate": "2014-06-03",
"id": "20140603",
"iso": "20140603",
"name": "2014-06-03",
+ "periodType": "DAILY",
"startDate": "2014-06-03",
},
Object {
+ "displayName": "June 4, 2014",
"endDate": "2014-06-04",
"id": "20140604",
"iso": "20140604",
"name": "2014-06-04",
+ "periodType": "DAILY",
"startDate": "2014-06-04",
},
Object {
+ "displayName": "June 5, 2014",
"endDate": "2014-06-05",
"id": "20140605",
"iso": "20140605",
"name": "2014-06-05",
+ "periodType": "DAILY",
"startDate": "2014-06-05",
},
Object {
+ "displayName": "June 6, 2014",
"endDate": "2014-06-06",
"id": "20140606",
"iso": "20140606",
"name": "2014-06-06",
+ "periodType": "DAILY",
"startDate": "2014-06-06",
},
Object {
+ "displayName": "June 7, 2014",
"endDate": "2014-06-07",
"id": "20140607",
"iso": "20140607",
"name": "2014-06-07",
+ "periodType": "DAILY",
"startDate": "2014-06-07",
},
Object {
+ "displayName": "June 8, 2014",
"endDate": "2014-06-08",
"id": "20140608",
"iso": "20140608",
"name": "2014-06-08",
+ "periodType": "DAILY",
"startDate": "2014-06-08",
},
Object {
+ "displayName": "June 9, 2014",
"endDate": "2014-06-09",
"id": "20140609",
"iso": "20140609",
"name": "2014-06-09",
+ "periodType": "DAILY",
"startDate": "2014-06-09",
},
Object {
+ "displayName": "June 10, 2014",
"endDate": "2014-06-10",
"id": "20140610",
"iso": "20140610",
"name": "2014-06-10",
+ "periodType": "DAILY",
"startDate": "2014-06-10",
},
Object {
+ "displayName": "June 11, 2014",
"endDate": "2014-06-11",
"id": "20140611",
"iso": "20140611",
"name": "2014-06-11",
+ "periodType": "DAILY",
"startDate": "2014-06-11",
},
Object {
+ "displayName": "June 12, 2014",
"endDate": "2014-06-12",
"id": "20140612",
"iso": "20140612",
"name": "2014-06-12",
+ "periodType": "DAILY",
"startDate": "2014-06-12",
},
Object {
+ "displayName": "June 13, 2014",
"endDate": "2014-06-13",
"id": "20140613",
"iso": "20140613",
"name": "2014-06-13",
+ "periodType": "DAILY",
"startDate": "2014-06-13",
},
Object {
+ "displayName": "June 14, 2014",
"endDate": "2014-06-14",
"id": "20140614",
"iso": "20140614",
"name": "2014-06-14",
+ "periodType": "DAILY",
"startDate": "2014-06-14",
},
Object {
+ "displayName": "June 15, 2014",
"endDate": "2014-06-15",
"id": "20140615",
"iso": "20140615",
"name": "2014-06-15",
+ "periodType": "DAILY",
"startDate": "2014-06-15",
},
Object {
+ "displayName": "June 16, 2014",
"endDate": "2014-06-16",
"id": "20140616",
"iso": "20140616",
"name": "2014-06-16",
+ "periodType": "DAILY",
"startDate": "2014-06-16",
},
Object {
+ "displayName": "June 17, 2014",
"endDate": "2014-06-17",
"id": "20140617",
"iso": "20140617",
"name": "2014-06-17",
+ "periodType": "DAILY",
"startDate": "2014-06-17",
},
Object {
+ "displayName": "June 18, 2014",
"endDate": "2014-06-18",
"id": "20140618",
"iso": "20140618",
"name": "2014-06-18",
+ "periodType": "DAILY",
"startDate": "2014-06-18",
},
Object {
+ "displayName": "June 19, 2014",
"endDate": "2014-06-19",
"id": "20140619",
"iso": "20140619",
"name": "2014-06-19",
+ "periodType": "DAILY",
"startDate": "2014-06-19",
},
Object {
+ "displayName": "June 20, 2014",
"endDate": "2014-06-20",
"id": "20140620",
"iso": "20140620",
"name": "2014-06-20",
+ "periodType": "DAILY",
"startDate": "2014-06-20",
},
Object {
+ "displayName": "June 21, 2014",
"endDate": "2014-06-21",
"id": "20140621",
"iso": "20140621",
"name": "2014-06-21",
+ "periodType": "DAILY",
"startDate": "2014-06-21",
},
Object {
+ "displayName": "June 22, 2014",
"endDate": "2014-06-22",
"id": "20140622",
"iso": "20140622",
"name": "2014-06-22",
+ "periodType": "DAILY",
"startDate": "2014-06-22",
},
Object {
+ "displayName": "June 23, 2014",
"endDate": "2014-06-23",
"id": "20140623",
"iso": "20140623",
"name": "2014-06-23",
+ "periodType": "DAILY",
"startDate": "2014-06-23",
},
Object {
+ "displayName": "June 24, 2014",
"endDate": "2014-06-24",
"id": "20140624",
"iso": "20140624",
"name": "2014-06-24",
+ "periodType": "DAILY",
"startDate": "2014-06-24",
},
Object {
+ "displayName": "June 25, 2014",
"endDate": "2014-06-25",
"id": "20140625",
"iso": "20140625",
"name": "2014-06-25",
+ "periodType": "DAILY",
"startDate": "2014-06-25",
},
Object {
+ "displayName": "June 26, 2014",
"endDate": "2014-06-26",
"id": "20140626",
"iso": "20140626",
"name": "2014-06-26",
+ "periodType": "DAILY",
"startDate": "2014-06-26",
},
Object {
+ "displayName": "June 27, 2014",
"endDate": "2014-06-27",
"id": "20140627",
"iso": "20140627",
"name": "2014-06-27",
+ "periodType": "DAILY",
"startDate": "2014-06-27",
},
Object {
+ "displayName": "June 28, 2014",
"endDate": "2014-06-28",
"id": "20140628",
"iso": "20140628",
"name": "2014-06-28",
+ "periodType": "DAILY",
"startDate": "2014-06-28",
},
Object {
+ "displayName": "June 29, 2014",
"endDate": "2014-06-29",
"id": "20140629",
"iso": "20140629",
"name": "2014-06-29",
+ "periodType": "DAILY",
"startDate": "2014-06-29",
},
Object {
+ "displayName": "June 30, 2014",
"endDate": "2014-06-30",
"id": "20140630",
"iso": "20140630",
"name": "2014-06-30",
+ "periodType": "DAILY",
"startDate": "2014-06-30",
},
Object {
+ "displayName": "July 1, 2014",
"endDate": "2014-07-01",
"id": "20140701",
"iso": "20140701",
"name": "2014-07-01",
+ "periodType": "DAILY",
"startDate": "2014-07-01",
},
Object {
+ "displayName": "July 2, 2014",
"endDate": "2014-07-02",
"id": "20140702",
"iso": "20140702",
"name": "2014-07-02",
+ "periodType": "DAILY",
"startDate": "2014-07-02",
},
Object {
+ "displayName": "July 3, 2014",
"endDate": "2014-07-03",
"id": "20140703",
"iso": "20140703",
"name": "2014-07-03",
+ "periodType": "DAILY",
"startDate": "2014-07-03",
},
Object {
+ "displayName": "July 4, 2014",
"endDate": "2014-07-04",
"id": "20140704",
"iso": "20140704",
"name": "2014-07-04",
+ "periodType": "DAILY",
"startDate": "2014-07-04",
},
Object {
+ "displayName": "July 5, 2014",
"endDate": "2014-07-05",
"id": "20140705",
"iso": "20140705",
"name": "2014-07-05",
+ "periodType": "DAILY",
"startDate": "2014-07-05",
},
Object {
+ "displayName": "July 6, 2014",
"endDate": "2014-07-06",
"id": "20140706",
"iso": "20140706",
"name": "2014-07-06",
+ "periodType": "DAILY",
"startDate": "2014-07-06",
},
Object {
+ "displayName": "July 7, 2014",
"endDate": "2014-07-07",
"id": "20140707",
"iso": "20140707",
"name": "2014-07-07",
+ "periodType": "DAILY",
"startDate": "2014-07-07",
},
Object {
+ "displayName": "July 8, 2014",
"endDate": "2014-07-08",
"id": "20140708",
"iso": "20140708",
"name": "2014-07-08",
+ "periodType": "DAILY",
"startDate": "2014-07-08",
},
Object {
+ "displayName": "July 9, 2014",
"endDate": "2014-07-09",
"id": "20140709",
"iso": "20140709",
"name": "2014-07-09",
+ "periodType": "DAILY",
"startDate": "2014-07-09",
},
Object {
+ "displayName": "July 10, 2014",
"endDate": "2014-07-10",
"id": "20140710",
"iso": "20140710",
"name": "2014-07-10",
+ "periodType": "DAILY",
"startDate": "2014-07-10",
},
Object {
+ "displayName": "July 11, 2014",
"endDate": "2014-07-11",
"id": "20140711",
"iso": "20140711",
"name": "2014-07-11",
+ "periodType": "DAILY",
"startDate": "2014-07-11",
},
Object {
+ "displayName": "July 12, 2014",
"endDate": "2014-07-12",
"id": "20140712",
"iso": "20140712",
"name": "2014-07-12",
+ "periodType": "DAILY",
"startDate": "2014-07-12",
},
Object {
+ "displayName": "July 13, 2014",
"endDate": "2014-07-13",
"id": "20140713",
"iso": "20140713",
"name": "2014-07-13",
+ "periodType": "DAILY",
"startDate": "2014-07-13",
},
Object {
+ "displayName": "July 14, 2014",
"endDate": "2014-07-14",
"id": "20140714",
"iso": "20140714",
"name": "2014-07-14",
+ "periodType": "DAILY",
"startDate": "2014-07-14",
},
Object {
+ "displayName": "July 15, 2014",
"endDate": "2014-07-15",
"id": "20140715",
"iso": "20140715",
"name": "2014-07-15",
+ "periodType": "DAILY",
"startDate": "2014-07-15",
},
Object {
+ "displayName": "July 16, 2014",
"endDate": "2014-07-16",
"id": "20140716",
"iso": "20140716",
"name": "2014-07-16",
+ "periodType": "DAILY",
"startDate": "2014-07-16",
},
Object {
+ "displayName": "July 17, 2014",
"endDate": "2014-07-17",
"id": "20140717",
"iso": "20140717",
"name": "2014-07-17",
+ "periodType": "DAILY",
"startDate": "2014-07-17",
},
Object {
+ "displayName": "July 18, 2014",
"endDate": "2014-07-18",
"id": "20140718",
"iso": "20140718",
"name": "2014-07-18",
+ "periodType": "DAILY",
"startDate": "2014-07-18",
},
Object {
+ "displayName": "July 19, 2014",
"endDate": "2014-07-19",
"id": "20140719",
"iso": "20140719",
"name": "2014-07-19",
+ "periodType": "DAILY",
"startDate": "2014-07-19",
},
Object {
+ "displayName": "July 20, 2014",
"endDate": "2014-07-20",
"id": "20140720",
"iso": "20140720",
"name": "2014-07-20",
+ "periodType": "DAILY",
"startDate": "2014-07-20",
},
Object {
+ "displayName": "July 21, 2014",
"endDate": "2014-07-21",
"id": "20140721",
"iso": "20140721",
"name": "2014-07-21",
+ "periodType": "DAILY",
"startDate": "2014-07-21",
},
Object {
+ "displayName": "July 22, 2014",
"endDate": "2014-07-22",
"id": "20140722",
"iso": "20140722",
"name": "2014-07-22",
+ "periodType": "DAILY",
"startDate": "2014-07-22",
},
Object {
+ "displayName": "July 23, 2014",
"endDate": "2014-07-23",
"id": "20140723",
"iso": "20140723",
"name": "2014-07-23",
+ "periodType": "DAILY",
"startDate": "2014-07-23",
},
Object {
+ "displayName": "July 24, 2014",
"endDate": "2014-07-24",
"id": "20140724",
"iso": "20140724",
"name": "2014-07-24",
+ "periodType": "DAILY",
"startDate": "2014-07-24",
},
Object {
+ "displayName": "July 25, 2014",
"endDate": "2014-07-25",
"id": "20140725",
"iso": "20140725",
"name": "2014-07-25",
+ "periodType": "DAILY",
"startDate": "2014-07-25",
},
Object {
+ "displayName": "July 26, 2014",
"endDate": "2014-07-26",
"id": "20140726",
"iso": "20140726",
"name": "2014-07-26",
+ "periodType": "DAILY",
"startDate": "2014-07-26",
},
Object {
+ "displayName": "July 27, 2014",
"endDate": "2014-07-27",
"id": "20140727",
"iso": "20140727",
"name": "2014-07-27",
+ "periodType": "DAILY",
"startDate": "2014-07-27",
},
Object {
+ "displayName": "July 28, 2014",
"endDate": "2014-07-28",
"id": "20140728",
"iso": "20140728",
"name": "2014-07-28",
+ "periodType": "DAILY",
"startDate": "2014-07-28",
},
Object {
+ "displayName": "July 29, 2014",
"endDate": "2014-07-29",
"id": "20140729",
"iso": "20140729",
"name": "2014-07-29",
+ "periodType": "DAILY",
"startDate": "2014-07-29",
},
Object {
+ "displayName": "July 30, 2014",
"endDate": "2014-07-30",
"id": "20140730",
"iso": "20140730",
"name": "2014-07-30",
+ "periodType": "DAILY",
"startDate": "2014-07-30",
},
Object {
+ "displayName": "July 31, 2014",
"endDate": "2014-07-31",
"id": "20140731",
"iso": "20140731",
"name": "2014-07-31",
+ "periodType": "DAILY",
"startDate": "2014-07-31",
},
Object {
+ "displayName": "August 1, 2014",
"endDate": "2014-08-01",
"id": "20140801",
"iso": "20140801",
"name": "2014-08-01",
+ "periodType": "DAILY",
"startDate": "2014-08-01",
},
Object {
+ "displayName": "August 2, 2014",
"endDate": "2014-08-02",
"id": "20140802",
"iso": "20140802",
"name": "2014-08-02",
+ "periodType": "DAILY",
"startDate": "2014-08-02",
},
Object {
+ "displayName": "August 3, 2014",
"endDate": "2014-08-03",
"id": "20140803",
"iso": "20140803",
"name": "2014-08-03",
+ "periodType": "DAILY",
"startDate": "2014-08-03",
},
Object {
+ "displayName": "August 4, 2014",
"endDate": "2014-08-04",
"id": "20140804",
"iso": "20140804",
"name": "2014-08-04",
+ "periodType": "DAILY",
"startDate": "2014-08-04",
},
Object {
+ "displayName": "August 5, 2014",
"endDate": "2014-08-05",
"id": "20140805",
"iso": "20140805",
"name": "2014-08-05",
+ "periodType": "DAILY",
"startDate": "2014-08-05",
},
Object {
+ "displayName": "August 6, 2014",
"endDate": "2014-08-06",
"id": "20140806",
"iso": "20140806",
"name": "2014-08-06",
+ "periodType": "DAILY",
"startDate": "2014-08-06",
},
Object {
+ "displayName": "August 7, 2014",
"endDate": "2014-08-07",
"id": "20140807",
"iso": "20140807",
"name": "2014-08-07",
+ "periodType": "DAILY",
"startDate": "2014-08-07",
},
Object {
+ "displayName": "August 8, 2014",
"endDate": "2014-08-08",
"id": "20140808",
"iso": "20140808",
"name": "2014-08-08",
+ "periodType": "DAILY",
"startDate": "2014-08-08",
},
Object {
+ "displayName": "August 9, 2014",
"endDate": "2014-08-09",
"id": "20140809",
"iso": "20140809",
"name": "2014-08-09",
+ "periodType": "DAILY",
"startDate": "2014-08-09",
},
Object {
+ "displayName": "August 10, 2014",
"endDate": "2014-08-10",
"id": "20140810",
"iso": "20140810",
"name": "2014-08-10",
+ "periodType": "DAILY",
"startDate": "2014-08-10",
},
Object {
+ "displayName": "August 11, 2014",
"endDate": "2014-08-11",
"id": "20140811",
"iso": "20140811",
"name": "2014-08-11",
+ "periodType": "DAILY",
"startDate": "2014-08-11",
},
Object {
+ "displayName": "August 12, 2014",
"endDate": "2014-08-12",
"id": "20140812",
"iso": "20140812",
"name": "2014-08-12",
+ "periodType": "DAILY",
"startDate": "2014-08-12",
},
Object {
+ "displayName": "August 13, 2014",
"endDate": "2014-08-13",
"id": "20140813",
"iso": "20140813",
"name": "2014-08-13",
+ "periodType": "DAILY",
"startDate": "2014-08-13",
},
Object {
+ "displayName": "August 14, 2014",
"endDate": "2014-08-14",
"id": "20140814",
"iso": "20140814",
"name": "2014-08-14",
+ "periodType": "DAILY",
"startDate": "2014-08-14",
},
Object {
+ "displayName": "August 15, 2014",
"endDate": "2014-08-15",
"id": "20140815",
"iso": "20140815",
"name": "2014-08-15",
+ "periodType": "DAILY",
"startDate": "2014-08-15",
},
Object {
+ "displayName": "August 16, 2014",
"endDate": "2014-08-16",
"id": "20140816",
"iso": "20140816",
"name": "2014-08-16",
+ "periodType": "DAILY",
"startDate": "2014-08-16",
},
Object {
+ "displayName": "August 17, 2014",
"endDate": "2014-08-17",
"id": "20140817",
"iso": "20140817",
"name": "2014-08-17",
+ "periodType": "DAILY",
"startDate": "2014-08-17",
},
Object {
+ "displayName": "August 18, 2014",
"endDate": "2014-08-18",
"id": "20140818",
"iso": "20140818",
"name": "2014-08-18",
+ "periodType": "DAILY",
"startDate": "2014-08-18",
},
Object {
+ "displayName": "August 19, 2014",
"endDate": "2014-08-19",
"id": "20140819",
"iso": "20140819",
"name": "2014-08-19",
+ "periodType": "DAILY",
"startDate": "2014-08-19",
},
Object {
+ "displayName": "August 20, 2014",
"endDate": "2014-08-20",
"id": "20140820",
"iso": "20140820",
"name": "2014-08-20",
+ "periodType": "DAILY",
"startDate": "2014-08-20",
},
Object {
+ "displayName": "August 21, 2014",
"endDate": "2014-08-21",
"id": "20140821",
"iso": "20140821",
"name": "2014-08-21",
+ "periodType": "DAILY",
"startDate": "2014-08-21",
},
Object {
+ "displayName": "August 22, 2014",
"endDate": "2014-08-22",
"id": "20140822",
"iso": "20140822",
"name": "2014-08-22",
+ "periodType": "DAILY",
"startDate": "2014-08-22",
},
Object {
+ "displayName": "August 23, 2014",
"endDate": "2014-08-23",
"id": "20140823",
"iso": "20140823",
"name": "2014-08-23",
+ "periodType": "DAILY",
"startDate": "2014-08-23",
},
Object {
+ "displayName": "August 24, 2014",
"endDate": "2014-08-24",
"id": "20140824",
"iso": "20140824",
"name": "2014-08-24",
+ "periodType": "DAILY",
"startDate": "2014-08-24",
},
Object {
+ "displayName": "August 25, 2014",
"endDate": "2014-08-25",
"id": "20140825",
"iso": "20140825",
"name": "2014-08-25",
+ "periodType": "DAILY",
"startDate": "2014-08-25",
},
Object {
+ "displayName": "August 26, 2014",
"endDate": "2014-08-26",
"id": "20140826",
"iso": "20140826",
"name": "2014-08-26",
+ "periodType": "DAILY",
"startDate": "2014-08-26",
},
Object {
+ "displayName": "August 27, 2014",
"endDate": "2014-08-27",
"id": "20140827",
"iso": "20140827",
"name": "2014-08-27",
+ "periodType": "DAILY",
"startDate": "2014-08-27",
},
Object {
+ "displayName": "August 28, 2014",
"endDate": "2014-08-28",
"id": "20140828",
"iso": "20140828",
"name": "2014-08-28",
+ "periodType": "DAILY",
"startDate": "2014-08-28",
},
Object {
+ "displayName": "August 29, 2014",
"endDate": "2014-08-29",
"id": "20140829",
"iso": "20140829",
"name": "2014-08-29",
+ "periodType": "DAILY",
"startDate": "2014-08-29",
},
Object {
+ "displayName": "August 30, 2014",
"endDate": "2014-08-30",
"id": "20140830",
"iso": "20140830",
"name": "2014-08-30",
+ "periodType": "DAILY",
"startDate": "2014-08-30",
},
Object {
+ "displayName": "August 31, 2014",
"endDate": "2014-08-31",
"id": "20140831",
"iso": "20140831",
"name": "2014-08-31",
+ "periodType": "DAILY",
"startDate": "2014-08-31",
},
Object {
+ "displayName": "September 1, 2014",
"endDate": "2014-09-01",
"id": "20140901",
"iso": "20140901",
"name": "2014-09-01",
+ "periodType": "DAILY",
"startDate": "2014-09-01",
},
Object {
+ "displayName": "September 2, 2014",
"endDate": "2014-09-02",
"id": "20140902",
"iso": "20140902",
"name": "2014-09-02",
+ "periodType": "DAILY",
"startDate": "2014-09-02",
},
Object {
+ "displayName": "September 3, 2014",
"endDate": "2014-09-03",
"id": "20140903",
"iso": "20140903",
"name": "2014-09-03",
+ "periodType": "DAILY",
"startDate": "2014-09-03",
},
Object {
+ "displayName": "September 4, 2014",
"endDate": "2014-09-04",
"id": "20140904",
"iso": "20140904",
"name": "2014-09-04",
+ "periodType": "DAILY",
"startDate": "2014-09-04",
},
Object {
+ "displayName": "September 5, 2014",
"endDate": "2014-09-05",
"id": "20140905",
"iso": "20140905",
"name": "2014-09-05",
+ "periodType": "DAILY",
"startDate": "2014-09-05",
},
Object {
+ "displayName": "September 6, 2014",
"endDate": "2014-09-06",
"id": "20140906",
"iso": "20140906",
"name": "2014-09-06",
+ "periodType": "DAILY",
"startDate": "2014-09-06",
},
Object {
+ "displayName": "September 7, 2014",
"endDate": "2014-09-07",
"id": "20140907",
"iso": "20140907",
"name": "2014-09-07",
+ "periodType": "DAILY",
"startDate": "2014-09-07",
},
Object {
+ "displayName": "September 8, 2014",
"endDate": "2014-09-08",
"id": "20140908",
"iso": "20140908",
"name": "2014-09-08",
+ "periodType": "DAILY",
"startDate": "2014-09-08",
},
Object {
+ "displayName": "September 9, 2014",
"endDate": "2014-09-09",
"id": "20140909",
"iso": "20140909",
"name": "2014-09-09",
+ "periodType": "DAILY",
"startDate": "2014-09-09",
},
Object {
+ "displayName": "September 10, 2014",
"endDate": "2014-09-10",
"id": "20140910",
"iso": "20140910",
"name": "2014-09-10",
+ "periodType": "DAILY",
"startDate": "2014-09-10",
},
Object {
+ "displayName": "September 11, 2014",
"endDate": "2014-09-11",
"id": "20140911",
"iso": "20140911",
"name": "2014-09-11",
+ "periodType": "DAILY",
"startDate": "2014-09-11",
},
Object {
+ "displayName": "September 12, 2014",
"endDate": "2014-09-12",
"id": "20140912",
"iso": "20140912",
"name": "2014-09-12",
+ "periodType": "DAILY",
"startDate": "2014-09-12",
},
Object {
+ "displayName": "September 13, 2014",
"endDate": "2014-09-13",
"id": "20140913",
"iso": "20140913",
"name": "2014-09-13",
+ "periodType": "DAILY",
"startDate": "2014-09-13",
},
Object {
+ "displayName": "September 14, 2014",
"endDate": "2014-09-14",
"id": "20140914",
"iso": "20140914",
"name": "2014-09-14",
+ "periodType": "DAILY",
"startDate": "2014-09-14",
},
Object {
+ "displayName": "September 15, 2014",
"endDate": "2014-09-15",
"id": "20140915",
"iso": "20140915",
"name": "2014-09-15",
+ "periodType": "DAILY",
"startDate": "2014-09-15",
},
Object {
+ "displayName": "September 16, 2014",
"endDate": "2014-09-16",
"id": "20140916",
"iso": "20140916",
"name": "2014-09-16",
+ "periodType": "DAILY",
"startDate": "2014-09-16",
},
Object {
+ "displayName": "September 17, 2014",
"endDate": "2014-09-17",
"id": "20140917",
"iso": "20140917",
"name": "2014-09-17",
+ "periodType": "DAILY",
"startDate": "2014-09-17",
},
Object {
+ "displayName": "September 18, 2014",
"endDate": "2014-09-18",
"id": "20140918",
"iso": "20140918",
"name": "2014-09-18",
+ "periodType": "DAILY",
"startDate": "2014-09-18",
},
Object {
+ "displayName": "September 19, 2014",
"endDate": "2014-09-19",
"id": "20140919",
"iso": "20140919",
"name": "2014-09-19",
+ "periodType": "DAILY",
"startDate": "2014-09-19",
},
Object {
+ "displayName": "September 20, 2014",
"endDate": "2014-09-20",
"id": "20140920",
"iso": "20140920",
"name": "2014-09-20",
+ "periodType": "DAILY",
"startDate": "2014-09-20",
},
Object {
+ "displayName": "September 21, 2014",
"endDate": "2014-09-21",
"id": "20140921",
"iso": "20140921",
"name": "2014-09-21",
+ "periodType": "DAILY",
"startDate": "2014-09-21",
},
Object {
+ "displayName": "September 22, 2014",
"endDate": "2014-09-22",
"id": "20140922",
"iso": "20140922",
"name": "2014-09-22",
+ "periodType": "DAILY",
"startDate": "2014-09-22",
},
Object {
+ "displayName": "September 23, 2014",
"endDate": "2014-09-23",
"id": "20140923",
"iso": "20140923",
"name": "2014-09-23",
+ "periodType": "DAILY",
"startDate": "2014-09-23",
},
Object {
+ "displayName": "September 24, 2014",
"endDate": "2014-09-24",
"id": "20140924",
"iso": "20140924",
"name": "2014-09-24",
+ "periodType": "DAILY",
"startDate": "2014-09-24",
},
Object {
+ "displayName": "September 25, 2014",
"endDate": "2014-09-25",
"id": "20140925",
"iso": "20140925",
"name": "2014-09-25",
+ "periodType": "DAILY",
"startDate": "2014-09-25",
},
Object {
+ "displayName": "September 26, 2014",
"endDate": "2014-09-26",
"id": "20140926",
"iso": "20140926",
"name": "2014-09-26",
+ "periodType": "DAILY",
"startDate": "2014-09-26",
},
Object {
+ "displayName": "September 27, 2014",
"endDate": "2014-09-27",
"id": "20140927",
"iso": "20140927",
"name": "2014-09-27",
+ "periodType": "DAILY",
"startDate": "2014-09-27",
},
Object {
+ "displayName": "September 28, 2014",
"endDate": "2014-09-28",
"id": "20140928",
"iso": "20140928",
"name": "2014-09-28",
+ "periodType": "DAILY",
"startDate": "2014-09-28",
},
Object {
+ "displayName": "September 29, 2014",
"endDate": "2014-09-29",
"id": "20140929",
"iso": "20140929",
"name": "2014-09-29",
+ "periodType": "DAILY",
"startDate": "2014-09-29",
},
Object {
+ "displayName": "September 30, 2014",
"endDate": "2014-09-30",
"id": "20140930",
"iso": "20140930",
"name": "2014-09-30",
+ "periodType": "DAILY",
"startDate": "2014-09-30",
},
Object {
+ "displayName": "October 1, 2014",
"endDate": "2014-10-01",
"id": "20141001",
"iso": "20141001",
"name": "2014-10-01",
+ "periodType": "DAILY",
"startDate": "2014-10-01",
},
Object {
+ "displayName": "October 2, 2014",
"endDate": "2014-10-02",
"id": "20141002",
"iso": "20141002",
"name": "2014-10-02",
+ "periodType": "DAILY",
"startDate": "2014-10-02",
},
Object {
+ "displayName": "October 3, 2014",
"endDate": "2014-10-03",
"id": "20141003",
"iso": "20141003",
"name": "2014-10-03",
+ "periodType": "DAILY",
"startDate": "2014-10-03",
},
Object {
+ "displayName": "October 4, 2014",
"endDate": "2014-10-04",
"id": "20141004",
"iso": "20141004",
"name": "2014-10-04",
+ "periodType": "DAILY",
"startDate": "2014-10-04",
},
Object {
+ "displayName": "October 5, 2014",
"endDate": "2014-10-05",
"id": "20141005",
"iso": "20141005",
"name": "2014-10-05",
+ "periodType": "DAILY",
"startDate": "2014-10-05",
},
Object {
+ "displayName": "October 6, 2014",
"endDate": "2014-10-06",
"id": "20141006",
"iso": "20141006",
"name": "2014-10-06",
+ "periodType": "DAILY",
"startDate": "2014-10-06",
},
Object {
+ "displayName": "October 7, 2014",
"endDate": "2014-10-07",
"id": "20141007",
"iso": "20141007",
"name": "2014-10-07",
+ "periodType": "DAILY",
"startDate": "2014-10-07",
},
Object {
+ "displayName": "October 8, 2014",
"endDate": "2014-10-08",
"id": "20141008",
"iso": "20141008",
"name": "2014-10-08",
+ "periodType": "DAILY",
"startDate": "2014-10-08",
},
Object {
+ "displayName": "October 9, 2014",
"endDate": "2014-10-09",
"id": "20141009",
"iso": "20141009",
"name": "2014-10-09",
+ "periodType": "DAILY",
"startDate": "2014-10-09",
},
Object {
+ "displayName": "October 10, 2014",
"endDate": "2014-10-10",
"id": "20141010",
"iso": "20141010",
"name": "2014-10-10",
+ "periodType": "DAILY",
"startDate": "2014-10-10",
},
Object {
+ "displayName": "October 11, 2014",
"endDate": "2014-10-11",
"id": "20141011",
"iso": "20141011",
"name": "2014-10-11",
+ "periodType": "DAILY",
"startDate": "2014-10-11",
},
Object {
+ "displayName": "October 12, 2014",
"endDate": "2014-10-12",
"id": "20141012",
"iso": "20141012",
"name": "2014-10-12",
+ "periodType": "DAILY",
"startDate": "2014-10-12",
},
Object {
+ "displayName": "October 13, 2014",
"endDate": "2014-10-13",
"id": "20141013",
"iso": "20141013",
"name": "2014-10-13",
+ "periodType": "DAILY",
"startDate": "2014-10-13",
},
Object {
+ "displayName": "October 14, 2014",
"endDate": "2014-10-14",
"id": "20141014",
"iso": "20141014",
"name": "2014-10-14",
+ "periodType": "DAILY",
"startDate": "2014-10-14",
},
Object {
+ "displayName": "October 15, 2014",
"endDate": "2014-10-15",
"id": "20141015",
"iso": "20141015",
"name": "2014-10-15",
+ "periodType": "DAILY",
"startDate": "2014-10-15",
},
Object {
+ "displayName": "October 16, 2014",
"endDate": "2014-10-16",
"id": "20141016",
"iso": "20141016",
"name": "2014-10-16",
+ "periodType": "DAILY",
"startDate": "2014-10-16",
},
Object {
+ "displayName": "October 17, 2014",
"endDate": "2014-10-17",
"id": "20141017",
"iso": "20141017",
"name": "2014-10-17",
+ "periodType": "DAILY",
"startDate": "2014-10-17",
},
Object {
+ "displayName": "October 18, 2014",
"endDate": "2014-10-18",
"id": "20141018",
"iso": "20141018",
"name": "2014-10-18",
+ "periodType": "DAILY",
"startDate": "2014-10-18",
},
Object {
+ "displayName": "October 19, 2014",
"endDate": "2014-10-19",
"id": "20141019",
"iso": "20141019",
"name": "2014-10-19",
+ "periodType": "DAILY",
"startDate": "2014-10-19",
},
Object {
+ "displayName": "October 20, 2014",
"endDate": "2014-10-20",
"id": "20141020",
"iso": "20141020",
"name": "2014-10-20",
+ "periodType": "DAILY",
"startDate": "2014-10-20",
},
Object {
+ "displayName": "October 21, 2014",
"endDate": "2014-10-21",
"id": "20141021",
"iso": "20141021",
"name": "2014-10-21",
+ "periodType": "DAILY",
"startDate": "2014-10-21",
},
Object {
+ "displayName": "October 22, 2014",
"endDate": "2014-10-22",
"id": "20141022",
"iso": "20141022",
"name": "2014-10-22",
+ "periodType": "DAILY",
"startDate": "2014-10-22",
},
Object {
+ "displayName": "October 23, 2014",
"endDate": "2014-10-23",
"id": "20141023",
"iso": "20141023",
"name": "2014-10-23",
+ "periodType": "DAILY",
"startDate": "2014-10-23",
},
Object {
+ "displayName": "October 24, 2014",
"endDate": "2014-10-24",
"id": "20141024",
"iso": "20141024",
"name": "2014-10-24",
+ "periodType": "DAILY",
"startDate": "2014-10-24",
},
Object {
+ "displayName": "October 25, 2014",
"endDate": "2014-10-25",
"id": "20141025",
"iso": "20141025",
"name": "2014-10-25",
+ "periodType": "DAILY",
"startDate": "2014-10-25",
},
Object {
+ "displayName": "October 26, 2014",
"endDate": "2014-10-26",
"id": "20141026",
"iso": "20141026",
"name": "2014-10-26",
+ "periodType": "DAILY",
"startDate": "2014-10-26",
},
Object {
+ "displayName": "October 27, 2014",
"endDate": "2014-10-27",
"id": "20141027",
"iso": "20141027",
"name": "2014-10-27",
+ "periodType": "DAILY",
"startDate": "2014-10-27",
},
Object {
+ "displayName": "October 28, 2014",
"endDate": "2014-10-28",
"id": "20141028",
"iso": "20141028",
"name": "2014-10-28",
+ "periodType": "DAILY",
"startDate": "2014-10-28",
},
Object {
+ "displayName": "October 29, 2014",
"endDate": "2014-10-29",
"id": "20141029",
"iso": "20141029",
"name": "2014-10-29",
+ "periodType": "DAILY",
"startDate": "2014-10-29",
},
Object {
+ "displayName": "October 30, 2014",
"endDate": "2014-10-30",
"id": "20141030",
"iso": "20141030",
"name": "2014-10-30",
+ "periodType": "DAILY",
"startDate": "2014-10-30",
},
Object {
+ "displayName": "October 31, 2014",
"endDate": "2014-10-31",
"id": "20141031",
"iso": "20141031",
"name": "2014-10-31",
+ "periodType": "DAILY",
"startDate": "2014-10-31",
},
Object {
+ "displayName": "November 1, 2014",
"endDate": "2014-11-01",
"id": "20141101",
"iso": "20141101",
"name": "2014-11-01",
+ "periodType": "DAILY",
"startDate": "2014-11-01",
},
Object {
+ "displayName": "November 2, 2014",
"endDate": "2014-11-02",
"id": "20141102",
"iso": "20141102",
"name": "2014-11-02",
+ "periodType": "DAILY",
"startDate": "2014-11-02",
},
Object {
+ "displayName": "November 3, 2014",
"endDate": "2014-11-03",
"id": "20141103",
"iso": "20141103",
"name": "2014-11-03",
+ "periodType": "DAILY",
"startDate": "2014-11-03",
},
Object {
+ "displayName": "November 4, 2014",
"endDate": "2014-11-04",
"id": "20141104",
"iso": "20141104",
"name": "2014-11-04",
+ "periodType": "DAILY",
"startDate": "2014-11-04",
},
Object {
+ "displayName": "November 5, 2014",
"endDate": "2014-11-05",
"id": "20141105",
"iso": "20141105",
"name": "2014-11-05",
+ "periodType": "DAILY",
"startDate": "2014-11-05",
},
Object {
+ "displayName": "November 6, 2014",
"endDate": "2014-11-06",
"id": "20141106",
"iso": "20141106",
"name": "2014-11-06",
+ "periodType": "DAILY",
"startDate": "2014-11-06",
},
Object {
+ "displayName": "November 7, 2014",
"endDate": "2014-11-07",
"id": "20141107",
"iso": "20141107",
"name": "2014-11-07",
+ "periodType": "DAILY",
"startDate": "2014-11-07",
},
Object {
+ "displayName": "November 8, 2014",
"endDate": "2014-11-08",
"id": "20141108",
"iso": "20141108",
"name": "2014-11-08",
+ "periodType": "DAILY",
"startDate": "2014-11-08",
},
Object {
+ "displayName": "November 9, 2014",
"endDate": "2014-11-09",
"id": "20141109",
"iso": "20141109",
"name": "2014-11-09",
+ "periodType": "DAILY",
"startDate": "2014-11-09",
},
Object {
+ "displayName": "November 10, 2014",
"endDate": "2014-11-10",
"id": "20141110",
"iso": "20141110",
"name": "2014-11-10",
+ "periodType": "DAILY",
"startDate": "2014-11-10",
},
Object {
+ "displayName": "November 11, 2014",
"endDate": "2014-11-11",
"id": "20141111",
"iso": "20141111",
"name": "2014-11-11",
+ "periodType": "DAILY",
"startDate": "2014-11-11",
},
Object {
+ "displayName": "November 12, 2014",
"endDate": "2014-11-12",
"id": "20141112",
"iso": "20141112",
"name": "2014-11-12",
+ "periodType": "DAILY",
"startDate": "2014-11-12",
},
Object {
+ "displayName": "November 13, 2014",
"endDate": "2014-11-13",
"id": "20141113",
"iso": "20141113",
"name": "2014-11-13",
+ "periodType": "DAILY",
"startDate": "2014-11-13",
},
Object {
+ "displayName": "November 14, 2014",
"endDate": "2014-11-14",
"id": "20141114",
"iso": "20141114",
"name": "2014-11-14",
+ "periodType": "DAILY",
"startDate": "2014-11-14",
},
Object {
+ "displayName": "November 15, 2014",
"endDate": "2014-11-15",
"id": "20141115",
"iso": "20141115",
"name": "2014-11-15",
+ "periodType": "DAILY",
"startDate": "2014-11-15",
},
Object {
+ "displayName": "November 16, 2014",
"endDate": "2014-11-16",
"id": "20141116",
"iso": "20141116",
"name": "2014-11-16",
+ "periodType": "DAILY",
"startDate": "2014-11-16",
},
Object {
+ "displayName": "November 17, 2014",
"endDate": "2014-11-17",
"id": "20141117",
"iso": "20141117",
"name": "2014-11-17",
+ "periodType": "DAILY",
"startDate": "2014-11-17",
},
Object {
+ "displayName": "November 18, 2014",
"endDate": "2014-11-18",
"id": "20141118",
"iso": "20141118",
"name": "2014-11-18",
+ "periodType": "DAILY",
"startDate": "2014-11-18",
},
Object {
+ "displayName": "November 19, 2014",
"endDate": "2014-11-19",
"id": "20141119",
"iso": "20141119",
"name": "2014-11-19",
+ "periodType": "DAILY",
"startDate": "2014-11-19",
},
Object {
+ "displayName": "November 20, 2014",
"endDate": "2014-11-20",
"id": "20141120",
"iso": "20141120",
"name": "2014-11-20",
+ "periodType": "DAILY",
"startDate": "2014-11-20",
},
Object {
+ "displayName": "November 21, 2014",
"endDate": "2014-11-21",
"id": "20141121",
"iso": "20141121",
"name": "2014-11-21",
+ "periodType": "DAILY",
"startDate": "2014-11-21",
},
Object {
+ "displayName": "November 22, 2014",
"endDate": "2014-11-22",
"id": "20141122",
"iso": "20141122",
"name": "2014-11-22",
+ "periodType": "DAILY",
"startDate": "2014-11-22",
},
Object {
+ "displayName": "November 23, 2014",
"endDate": "2014-11-23",
"id": "20141123",
"iso": "20141123",
"name": "2014-11-23",
+ "periodType": "DAILY",
"startDate": "2014-11-23",
},
Object {
+ "displayName": "November 24, 2014",
"endDate": "2014-11-24",
"id": "20141124",
"iso": "20141124",
"name": "2014-11-24",
+ "periodType": "DAILY",
"startDate": "2014-11-24",
},
Object {
+ "displayName": "November 25, 2014",
"endDate": "2014-11-25",
"id": "20141125",
"iso": "20141125",
"name": "2014-11-25",
+ "periodType": "DAILY",
"startDate": "2014-11-25",
},
Object {
+ "displayName": "November 26, 2014",
"endDate": "2014-11-26",
"id": "20141126",
"iso": "20141126",
"name": "2014-11-26",
+ "periodType": "DAILY",
"startDate": "2014-11-26",
},
Object {
+ "displayName": "November 27, 2014",
"endDate": "2014-11-27",
"id": "20141127",
"iso": "20141127",
"name": "2014-11-27",
+ "periodType": "DAILY",
"startDate": "2014-11-27",
},
Object {
+ "displayName": "November 28, 2014",
"endDate": "2014-11-28",
"id": "20141128",
"iso": "20141128",
"name": "2014-11-28",
+ "periodType": "DAILY",
"startDate": "2014-11-28",
},
Object {
+ "displayName": "November 29, 2014",
"endDate": "2014-11-29",
"id": "20141129",
"iso": "20141129",
"name": "2014-11-29",
+ "periodType": "DAILY",
"startDate": "2014-11-29",
},
Object {
+ "displayName": "November 30, 2014",
"endDate": "2014-11-30",
"id": "20141130",
"iso": "20141130",
"name": "2014-11-30",
+ "periodType": "DAILY",
"startDate": "2014-11-30",
},
Object {
+ "displayName": "December 1, 2014",
"endDate": "2014-12-01",
"id": "20141201",
"iso": "20141201",
"name": "2014-12-01",
+ "periodType": "DAILY",
"startDate": "2014-12-01",
},
Object {
+ "displayName": "December 2, 2014",
"endDate": "2014-12-02",
"id": "20141202",
"iso": "20141202",
"name": "2014-12-02",
+ "periodType": "DAILY",
"startDate": "2014-12-02",
},
Object {
+ "displayName": "December 3, 2014",
"endDate": "2014-12-03",
"id": "20141203",
"iso": "20141203",
"name": "2014-12-03",
+ "periodType": "DAILY",
"startDate": "2014-12-03",
},
Object {
+ "displayName": "December 4, 2014",
"endDate": "2014-12-04",
"id": "20141204",
"iso": "20141204",
"name": "2014-12-04",
+ "periodType": "DAILY",
"startDate": "2014-12-04",
},
Object {
+ "displayName": "December 5, 2014",
"endDate": "2014-12-05",
"id": "20141205",
"iso": "20141205",
"name": "2014-12-05",
+ "periodType": "DAILY",
"startDate": "2014-12-05",
},
Object {
+ "displayName": "December 6, 2014",
"endDate": "2014-12-06",
"id": "20141206",
"iso": "20141206",
"name": "2014-12-06",
+ "periodType": "DAILY",
"startDate": "2014-12-06",
},
Object {
+ "displayName": "December 7, 2014",
"endDate": "2014-12-07",
"id": "20141207",
"iso": "20141207",
"name": "2014-12-07",
+ "periodType": "DAILY",
"startDate": "2014-12-07",
},
Object {
+ "displayName": "December 8, 2014",
"endDate": "2014-12-08",
"id": "20141208",
"iso": "20141208",
"name": "2014-12-08",
+ "periodType": "DAILY",
"startDate": "2014-12-08",
},
Object {
+ "displayName": "December 9, 2014",
"endDate": "2014-12-09",
"id": "20141209",
"iso": "20141209",
"name": "2014-12-09",
+ "periodType": "DAILY",
"startDate": "2014-12-09",
},
Object {
+ "displayName": "December 10, 2014",
"endDate": "2014-12-10",
"id": "20141210",
"iso": "20141210",
"name": "2014-12-10",
+ "periodType": "DAILY",
"startDate": "2014-12-10",
},
Object {
+ "displayName": "December 11, 2014",
"endDate": "2014-12-11",
"id": "20141211",
"iso": "20141211",
"name": "2014-12-11",
+ "periodType": "DAILY",
"startDate": "2014-12-11",
},
Object {
+ "displayName": "December 12, 2014",
"endDate": "2014-12-12",
"id": "20141212",
"iso": "20141212",
"name": "2014-12-12",
+ "periodType": "DAILY",
"startDate": "2014-12-12",
},
Object {
+ "displayName": "December 13, 2014",
"endDate": "2014-12-13",
"id": "20141213",
"iso": "20141213",
"name": "2014-12-13",
+ "periodType": "DAILY",
"startDate": "2014-12-13",
},
Object {
+ "displayName": "December 14, 2014",
"endDate": "2014-12-14",
"id": "20141214",
"iso": "20141214",
"name": "2014-12-14",
+ "periodType": "DAILY",
"startDate": "2014-12-14",
},
Object {
+ "displayName": "December 15, 2014",
"endDate": "2014-12-15",
"id": "20141215",
"iso": "20141215",
"name": "2014-12-15",
+ "periodType": "DAILY",
"startDate": "2014-12-15",
},
Object {
+ "displayName": "December 16, 2014",
"endDate": "2014-12-16",
"id": "20141216",
"iso": "20141216",
"name": "2014-12-16",
+ "periodType": "DAILY",
"startDate": "2014-12-16",
},
Object {
+ "displayName": "December 17, 2014",
"endDate": "2014-12-17",
"id": "20141217",
"iso": "20141217",
"name": "2014-12-17",
+ "periodType": "DAILY",
"startDate": "2014-12-17",
},
Object {
+ "displayName": "December 18, 2014",
"endDate": "2014-12-18",
"id": "20141218",
"iso": "20141218",
"name": "2014-12-18",
+ "periodType": "DAILY",
"startDate": "2014-12-18",
},
Object {
+ "displayName": "December 19, 2014",
"endDate": "2014-12-19",
"id": "20141219",
"iso": "20141219",
"name": "2014-12-19",
+ "periodType": "DAILY",
"startDate": "2014-12-19",
},
Object {
+ "displayName": "December 20, 2014",
"endDate": "2014-12-20",
"id": "20141220",
"iso": "20141220",
"name": "2014-12-20",
+ "periodType": "DAILY",
"startDate": "2014-12-20",
},
Object {
+ "displayName": "December 21, 2014",
"endDate": "2014-12-21",
"id": "20141221",
"iso": "20141221",
"name": "2014-12-21",
+ "periodType": "DAILY",
"startDate": "2014-12-21",
},
Object {
+ "displayName": "December 22, 2014",
"endDate": "2014-12-22",
"id": "20141222",
"iso": "20141222",
"name": "2014-12-22",
+ "periodType": "DAILY",
"startDate": "2014-12-22",
},
Object {
+ "displayName": "December 23, 2014",
"endDate": "2014-12-23",
"id": "20141223",
"iso": "20141223",
"name": "2014-12-23",
+ "periodType": "DAILY",
"startDate": "2014-12-23",
},
Object {
+ "displayName": "December 24, 2014",
"endDate": "2014-12-24",
"id": "20141224",
"iso": "20141224",
"name": "2014-12-24",
+ "periodType": "DAILY",
"startDate": "2014-12-24",
},
Object {
+ "displayName": "December 25, 2014",
"endDate": "2014-12-25",
"id": "20141225",
"iso": "20141225",
"name": "2014-12-25",
+ "periodType": "DAILY",
"startDate": "2014-12-25",
},
Object {
+ "displayName": "December 26, 2014",
"endDate": "2014-12-26",
"id": "20141226",
"iso": "20141226",
"name": "2014-12-26",
+ "periodType": "DAILY",
"startDate": "2014-12-26",
},
Object {
+ "displayName": "December 27, 2014",
"endDate": "2014-12-27",
"id": "20141227",
"iso": "20141227",
"name": "2014-12-27",
+ "periodType": "DAILY",
"startDate": "2014-12-27",
},
Object {
+ "displayName": "December 28, 2014",
"endDate": "2014-12-28",
"id": "20141228",
"iso": "20141228",
"name": "2014-12-28",
+ "periodType": "DAILY",
"startDate": "2014-12-28",
},
Object {
+ "displayName": "December 29, 2014",
"endDate": "2014-12-29",
"id": "20141229",
"iso": "20141229",
"name": "2014-12-29",
+ "periodType": "DAILY",
"startDate": "2014-12-29",
},
Object {
+ "displayName": "December 30, 2014",
"endDate": "2014-12-30",
"id": "20141230",
"iso": "20141230",
"name": "2014-12-30",
+ "periodType": "DAILY",
"startDate": "2014-12-30",
},
Object {
+ "displayName": "December 31, 2014",
"endDate": "2014-12-31",
"id": "20141231",
"iso": "20141231",
"name": "2014-12-31",
+ "periodType": "DAILY",
"startDate": "2014-12-31",
},
],
@@ -2815,63 +3609,93 @@ Object {
"name": "Financial year (Start April)",
"options": Array [
Object {
+ "displayName": "April 2005 - March 2006",
"endDate": "2006-03-31",
"id": "2005April",
+ "iso": "2005April",
"name": "April 2005 - March 2006",
+ "periodType": "FYAPR",
"startDate": "2005-04-01",
},
Object {
+ "displayName": "April 2006 - March 2007",
"endDate": "2007-03-31",
"id": "2006April",
+ "iso": "2006April",
"name": "April 2006 - March 2007",
+ "periodType": "FYAPR",
"startDate": "2006-04-01",
},
Object {
+ "displayName": "April 2007 - March 2008",
"endDate": "2008-03-31",
"id": "2007April",
+ "iso": "2007April",
"name": "April 2007 - March 2008",
+ "periodType": "FYAPR",
"startDate": "2007-04-01",
},
Object {
+ "displayName": "April 2008 - March 2009",
"endDate": "2009-03-31",
"id": "2008April",
+ "iso": "2008April",
"name": "April 2008 - March 2009",
+ "periodType": "FYAPR",
"startDate": "2008-04-01",
},
Object {
+ "displayName": "April 2009 - March 2010",
"endDate": "2010-03-31",
"id": "2009April",
+ "iso": "2009April",
"name": "April 2009 - March 2010",
+ "periodType": "FYAPR",
"startDate": "2009-04-01",
},
Object {
+ "displayName": "April 2010 - March 2011",
"endDate": "2011-03-31",
"id": "2010April",
+ "iso": "2010April",
"name": "April 2010 - March 2011",
+ "periodType": "FYAPR",
"startDate": "2010-04-01",
},
Object {
+ "displayName": "April 2011 - March 2012",
"endDate": "2012-03-31",
"id": "2011April",
+ "iso": "2011April",
"name": "April 2011 - March 2012",
+ "periodType": "FYAPR",
"startDate": "2011-04-01",
},
Object {
+ "displayName": "April 2012 - March 2013",
"endDate": "2013-03-31",
"id": "2012April",
+ "iso": "2012April",
"name": "April 2012 - March 2013",
+ "periodType": "FYAPR",
"startDate": "2012-04-01",
},
Object {
+ "displayName": "April 2013 - March 2014",
"endDate": "2014-03-31",
"id": "2013April",
+ "iso": "2013April",
"name": "April 2013 - March 2014",
+ "periodType": "FYAPR",
"startDate": "2013-04-01",
},
Object {
+ "displayName": "April 2014 - March 2015",
"endDate": "2015-03-31",
"id": "2014April",
+ "iso": "2014April",
"name": "April 2014 - March 2015",
+ "periodType": "FYAPR",
"startDate": "2014-04-01",
},
],
@@ -2885,63 +3709,93 @@ Object {
"name": "Financial year (Start July)",
"options": Array [
Object {
+ "displayName": "July 2005 - June 2006",
"endDate": "2006-06-30",
"id": "2005July",
+ "iso": "2005July",
"name": "July 2005 - June 2006",
+ "periodType": "FYJUL",
"startDate": "2005-07-01",
},
Object {
+ "displayName": "July 2006 - June 2007",
"endDate": "2007-06-30",
"id": "2006July",
+ "iso": "2006July",
"name": "July 2006 - June 2007",
+ "periodType": "FYJUL",
"startDate": "2006-07-01",
},
Object {
+ "displayName": "July 2007 - June 2008",
"endDate": "2008-06-30",
"id": "2007July",
+ "iso": "2007July",
"name": "July 2007 - June 2008",
+ "periodType": "FYJUL",
"startDate": "2007-07-01",
},
Object {
+ "displayName": "July 2008 - June 2009",
"endDate": "2009-06-30",
"id": "2008July",
+ "iso": "2008July",
"name": "July 2008 - June 2009",
+ "periodType": "FYJUL",
"startDate": "2008-07-01",
},
Object {
+ "displayName": "July 2009 - June 2010",
"endDate": "2010-06-30",
"id": "2009July",
+ "iso": "2009July",
"name": "July 2009 - June 2010",
+ "periodType": "FYJUL",
"startDate": "2009-07-01",
},
Object {
+ "displayName": "July 2010 - June 2011",
"endDate": "2011-06-30",
"id": "2010July",
+ "iso": "2010July",
"name": "July 2010 - June 2011",
+ "periodType": "FYJUL",
"startDate": "2010-07-01",
},
Object {
+ "displayName": "July 2011 - June 2012",
"endDate": "2012-06-30",
"id": "2011July",
+ "iso": "2011July",
"name": "July 2011 - June 2012",
+ "periodType": "FYJUL",
"startDate": "2011-07-01",
},
Object {
+ "displayName": "July 2012 - June 2013",
"endDate": "2013-06-30",
"id": "2012July",
+ "iso": "2012July",
"name": "July 2012 - June 2013",
+ "periodType": "FYJUL",
"startDate": "2012-07-01",
},
Object {
+ "displayName": "July 2013 - June 2014",
"endDate": "2014-06-30",
"id": "2013July",
+ "iso": "2013July",
"name": "July 2013 - June 2014",
+ "periodType": "FYJUL",
"startDate": "2013-07-01",
},
Object {
+ "displayName": "July 2014 - June 2015",
"endDate": "2015-06-30",
"id": "2014July",
+ "iso": "2014July",
"name": "July 2014 - June 2015",
+ "periodType": "FYJUL",
"startDate": "2014-07-01",
},
],
@@ -2955,63 +3809,93 @@ Object {
"name": "Financial year (Start November)",
"options": Array [
Object {
+ "displayName": "November 2005 - October 2006",
"endDate": "2006-10-31",
"id": "2005Nov",
+ "iso": "2005Nov",
"name": "November 2005 - October 2006",
+ "periodType": "FYNOV",
"startDate": "2005-11-01",
},
Object {
+ "displayName": "November 2006 - October 2007",
"endDate": "2007-10-31",
"id": "2006Nov",
+ "iso": "2006Nov",
"name": "November 2006 - October 2007",
+ "periodType": "FYNOV",
"startDate": "2006-11-01",
},
Object {
+ "displayName": "November 2007 - October 2008",
"endDate": "2008-10-31",
"id": "2007Nov",
+ "iso": "2007Nov",
"name": "November 2007 - October 2008",
+ "periodType": "FYNOV",
"startDate": "2007-11-01",
},
Object {
+ "displayName": "November 2008 - October 2009",
"endDate": "2009-10-31",
"id": "2008Nov",
+ "iso": "2008Nov",
"name": "November 2008 - October 2009",
+ "periodType": "FYNOV",
"startDate": "2008-11-01",
},
Object {
+ "displayName": "November 2009 - October 2010",
"endDate": "2010-10-31",
"id": "2009Nov",
+ "iso": "2009Nov",
"name": "November 2009 - October 2010",
+ "periodType": "FYNOV",
"startDate": "2009-11-01",
},
Object {
+ "displayName": "November 2010 - October 2011",
"endDate": "2011-10-31",
"id": "2010Nov",
+ "iso": "2010Nov",
"name": "November 2010 - October 2011",
+ "periodType": "FYNOV",
"startDate": "2010-11-01",
},
Object {
+ "displayName": "November 2011 - October 2012",
"endDate": "2012-10-31",
"id": "2011Nov",
+ "iso": "2011Nov",
"name": "November 2011 - October 2012",
+ "periodType": "FYNOV",
"startDate": "2011-11-01",
},
Object {
+ "displayName": "November 2012 - October 2013",
"endDate": "2013-10-31",
"id": "2012Nov",
+ "iso": "2012Nov",
"name": "November 2012 - October 2013",
+ "periodType": "FYNOV",
"startDate": "2012-11-01",
},
Object {
+ "displayName": "November 2013 - October 2014",
"endDate": "2014-10-31",
"id": "2013Nov",
+ "iso": "2013Nov",
"name": "November 2013 - October 2014",
+ "periodType": "FYNOV",
"startDate": "2013-11-01",
},
Object {
+ "displayName": "November 2014 - October 2015",
"endDate": "2015-10-31",
"id": "2014Nov",
+ "iso": "2014Nov",
"name": "November 2014 - October 2015",
+ "periodType": "FYNOV",
"startDate": "2014-11-01",
},
],
@@ -3025,63 +3909,93 @@ Object {
"name": "Financial year (Start October)",
"options": Array [
Object {
+ "displayName": "October 2005 - September 2006",
"endDate": "2006-09-30",
"id": "2005Oct",
+ "iso": "2005Oct",
"name": "October 2005 - September 2006",
+ "periodType": "FYOCT",
"startDate": "2005-10-01",
},
Object {
+ "displayName": "October 2006 - September 2007",
"endDate": "2007-09-30",
"id": "2006Oct",
+ "iso": "2006Oct",
"name": "October 2006 - September 2007",
+ "periodType": "FYOCT",
"startDate": "2006-10-01",
},
Object {
+ "displayName": "October 2007 - September 2008",
"endDate": "2008-09-30",
"id": "2007Oct",
+ "iso": "2007Oct",
"name": "October 2007 - September 2008",
+ "periodType": "FYOCT",
"startDate": "2007-10-01",
},
Object {
+ "displayName": "October 2008 - September 2009",
"endDate": "2009-09-30",
"id": "2008Oct",
+ "iso": "2008Oct",
"name": "October 2008 - September 2009",
+ "periodType": "FYOCT",
"startDate": "2008-10-01",
},
Object {
+ "displayName": "October 2009 - September 2010",
"endDate": "2010-09-30",
"id": "2009Oct",
+ "iso": "2009Oct",
"name": "October 2009 - September 2010",
+ "periodType": "FYOCT",
"startDate": "2009-10-01",
},
Object {
+ "displayName": "October 2010 - September 2011",
"endDate": "2011-09-30",
"id": "2010Oct",
+ "iso": "2010Oct",
"name": "October 2010 - September 2011",
+ "periodType": "FYOCT",
"startDate": "2010-10-01",
},
Object {
+ "displayName": "October 2011 - September 2012",
"endDate": "2012-09-30",
"id": "2011Oct",
+ "iso": "2011Oct",
"name": "October 2011 - September 2012",
+ "periodType": "FYOCT",
"startDate": "2011-10-01",
},
Object {
+ "displayName": "October 2012 - September 2013",
"endDate": "2013-09-30",
"id": "2012Oct",
+ "iso": "2012Oct",
"name": "October 2012 - September 2013",
+ "periodType": "FYOCT",
"startDate": "2012-10-01",
},
Object {
+ "displayName": "October 2013 - September 2014",
"endDate": "2014-09-30",
"id": "2013Oct",
+ "iso": "2013Oct",
"name": "October 2013 - September 2014",
+ "periodType": "FYOCT",
"startDate": "2013-10-01",
},
Object {
+ "displayName": "October 2014 - September 2015",
"endDate": "2015-09-30",
"id": "2014Oct",
+ "iso": "2014Oct",
"name": "October 2014 - September 2015",
+ "periodType": "FYOCT",
"startDate": "2014-10-01",
},
],
@@ -3095,87 +4009,111 @@ Object {
"name": "Monthly",
"options": Array [
Object {
+ "displayName": "January 2014",
"endDate": "2014-01-31",
"id": "201401",
"iso": "201401",
"name": "January 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-01-01",
},
Object {
+ "displayName": "February 2014",
"endDate": "2014-02-28",
"id": "201402",
"iso": "201402",
"name": "February 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-02-01",
},
Object {
+ "displayName": "March 2014",
"endDate": "2014-03-31",
"id": "201403",
"iso": "201403",
"name": "March 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-03-01",
},
Object {
+ "displayName": "April 2014",
"endDate": "2014-04-30",
"id": "201404",
"iso": "201404",
"name": "April 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-04-01",
},
Object {
+ "displayName": "May 2014",
"endDate": "2014-05-31",
"id": "201405",
"iso": "201405",
"name": "May 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-05-01",
},
Object {
+ "displayName": "June 2014",
"endDate": "2014-06-30",
"id": "201406",
"iso": "201406",
"name": "June 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-06-01",
},
Object {
+ "displayName": "July 2014",
"endDate": "2014-07-31",
"id": "201407",
"iso": "201407",
"name": "July 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-07-01",
},
Object {
+ "displayName": "August 2014",
"endDate": "2014-08-31",
"id": "201408",
"iso": "201408",
"name": "August 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-08-01",
},
Object {
+ "displayName": "September 2014",
"endDate": "2014-09-30",
"id": "201409",
"iso": "201409",
"name": "September 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-09-01",
},
Object {
+ "displayName": "October 2014",
"endDate": "2014-10-31",
"id": "201410",
"iso": "201410",
"name": "October 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-10-01",
},
Object {
+ "displayName": "November 2014",
"endDate": "2014-11-30",
"id": "201411",
"iso": "201411",
"name": "November 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-11-01",
},
Object {
+ "displayName": "December 2014",
"endDate": "2014-12-31",
"id": "201412",
"iso": "201412",
"name": "December 2014",
+ "periodType": "MONTHLY",
"startDate": "2014-12-01",
},
],
@@ -3189,31 +4127,39 @@ Object {
"name": "Quarterly",
"options": Array [
Object {
+ "displayName": "January - March 2014",
"endDate": "2014-03-31",
"id": "2014Q1",
"iso": "2014Q1",
"name": "January - March 2014",
+ "periodType": "QUARTERLY",
"startDate": "2014-01-01",
},
Object {
+ "displayName": "April - June 2014",
"endDate": "2014-06-30",
"id": "2014Q2",
"iso": "2014Q2",
"name": "April - June 2014",
+ "periodType": "QUARTERLY",
"startDate": "2014-04-01",
},
Object {
+ "displayName": "July - September 2014",
"endDate": "2014-09-30",
"id": "2014Q3",
"iso": "2014Q3",
"name": "July - September 2014",
+ "periodType": "QUARTERLY",
"startDate": "2014-07-01",
},
Object {
+ "displayName": "October - December 2014",
"endDate": "2014-12-31",
"id": "2014Q4",
"iso": "2014Q4",
"name": "October - December 2014",
+ "periodType": "QUARTERLY",
"startDate": "2014-10-01",
},
],
@@ -3227,17 +4173,21 @@ Object {
"name": "Six-monthly",
"options": Array [
Object {
+ "displayName": "January - June 2014",
"endDate": "2014-06-30",
"id": "2014S1",
"iso": "2014S1",
"name": "January - June 2014",
+ "periodType": "SIXMONTHLY",
"startDate": "2014-01-01",
},
Object {
+ "displayName": "July - December 2014",
"endDate": "2014-12-31",
"id": "2014S2",
"iso": "2014S2",
"name": "July - December 2014",
+ "periodType": "SIXMONTHLY",
"startDate": "2014-07-01",
},
],
@@ -3251,17 +4201,21 @@ Object {
"name": "Six-monthly April",
"options": Array [
Object {
+ "displayName": "April - September 2014",
"endDate": "2014-09-30",
"id": "2014AprilS1",
"iso": "2014AprilS1",
"name": "April - September 2014",
+ "periodType": "SIXMONTHLYAPR",
"startDate": "2014-04-01",
},
Object {
+ "displayName": "October 2014 - March 2015",
"endDate": "2015-03-31",
"id": "2014AprilS2",
"iso": "2014AprilS2",
"name": "October 2014 - March 2015",
+ "periodType": "SIXMONTHLYAPR",
"startDate": "2014-10-01",
},
],
@@ -3275,367 +4229,471 @@ Object {
"name": "Weekly",
"options": Array [
Object {
+ "displayName": "Week 1 - 2013-12-30 - 2014-01-05",
"endDate": "2014-01-05",
"id": "2014W1",
"iso": "2014W1",
"name": "Week 1 - 2013-12-30 - 2014-01-05",
+ "periodType": "WEEKLY",
"startDate": "2013-12-30",
},
Object {
+ "displayName": "Week 2 - 2014-01-06 - 2014-01-12",
"endDate": "2014-01-12",
"id": "2014W2",
"iso": "2014W2",
"name": "Week 2 - 2014-01-06 - 2014-01-12",
+ "periodType": "WEEKLY",
"startDate": "2014-01-06",
},
Object {
+ "displayName": "Week 3 - 2014-01-13 - 2014-01-19",
"endDate": "2014-01-19",
"id": "2014W3",
"iso": "2014W3",
"name": "Week 3 - 2014-01-13 - 2014-01-19",
+ "periodType": "WEEKLY",
"startDate": "2014-01-13",
},
Object {
+ "displayName": "Week 4 - 2014-01-20 - 2014-01-26",
"endDate": "2014-01-26",
"id": "2014W4",
"iso": "2014W4",
"name": "Week 4 - 2014-01-20 - 2014-01-26",
+ "periodType": "WEEKLY",
"startDate": "2014-01-20",
},
Object {
+ "displayName": "Week 5 - 2014-01-27 - 2014-02-02",
"endDate": "2014-02-02",
"id": "2014W5",
"iso": "2014W5",
"name": "Week 5 - 2014-01-27 - 2014-02-02",
+ "periodType": "WEEKLY",
"startDate": "2014-01-27",
},
Object {
+ "displayName": "Week 6 - 2014-02-03 - 2014-02-09",
"endDate": "2014-02-09",
"id": "2014W6",
"iso": "2014W6",
"name": "Week 6 - 2014-02-03 - 2014-02-09",
+ "periodType": "WEEKLY",
"startDate": "2014-02-03",
},
Object {
+ "displayName": "Week 7 - 2014-02-10 - 2014-02-16",
"endDate": "2014-02-16",
"id": "2014W7",
"iso": "2014W7",
"name": "Week 7 - 2014-02-10 - 2014-02-16",
+ "periodType": "WEEKLY",
"startDate": "2014-02-10",
},
Object {
+ "displayName": "Week 8 - 2014-02-17 - 2014-02-23",
"endDate": "2014-02-23",
"id": "2014W8",
"iso": "2014W8",
"name": "Week 8 - 2014-02-17 - 2014-02-23",
+ "periodType": "WEEKLY",
"startDate": "2014-02-17",
},
Object {
+ "displayName": "Week 9 - 2014-02-24 - 2014-03-02",
"endDate": "2014-03-02",
"id": "2014W9",
"iso": "2014W9",
"name": "Week 9 - 2014-02-24 - 2014-03-02",
+ "periodType": "WEEKLY",
"startDate": "2014-02-24",
},
Object {
+ "displayName": "Week 10 - 2014-03-03 - 2014-03-09",
"endDate": "2014-03-09",
"id": "2014W10",
"iso": "2014W10",
"name": "Week 10 - 2014-03-03 - 2014-03-09",
+ "periodType": "WEEKLY",
"startDate": "2014-03-03",
},
Object {
+ "displayName": "Week 11 - 2014-03-10 - 2014-03-16",
"endDate": "2014-03-16",
"id": "2014W11",
"iso": "2014W11",
"name": "Week 11 - 2014-03-10 - 2014-03-16",
+ "periodType": "WEEKLY",
"startDate": "2014-03-10",
},
Object {
+ "displayName": "Week 12 - 2014-03-17 - 2014-03-23",
"endDate": "2014-03-23",
"id": "2014W12",
"iso": "2014W12",
"name": "Week 12 - 2014-03-17 - 2014-03-23",
+ "periodType": "WEEKLY",
"startDate": "2014-03-17",
},
Object {
+ "displayName": "Week 13 - 2014-03-24 - 2014-03-30",
"endDate": "2014-03-30",
"id": "2014W13",
"iso": "2014W13",
"name": "Week 13 - 2014-03-24 - 2014-03-30",
+ "periodType": "WEEKLY",
"startDate": "2014-03-24",
},
Object {
+ "displayName": "Week 14 - 2014-03-31 - 2014-04-06",
"endDate": "2014-04-06",
"id": "2014W14",
"iso": "2014W14",
"name": "Week 14 - 2014-03-31 - 2014-04-06",
+ "periodType": "WEEKLY",
"startDate": "2014-03-31",
},
Object {
+ "displayName": "Week 15 - 2014-04-07 - 2014-04-13",
"endDate": "2014-04-13",
"id": "2014W15",
"iso": "2014W15",
"name": "Week 15 - 2014-04-07 - 2014-04-13",
+ "periodType": "WEEKLY",
"startDate": "2014-04-07",
},
Object {
+ "displayName": "Week 16 - 2014-04-14 - 2014-04-20",
"endDate": "2014-04-20",
"id": "2014W16",
"iso": "2014W16",
"name": "Week 16 - 2014-04-14 - 2014-04-20",
+ "periodType": "WEEKLY",
"startDate": "2014-04-14",
},
Object {
+ "displayName": "Week 17 - 2014-04-21 - 2014-04-27",
"endDate": "2014-04-27",
"id": "2014W17",
"iso": "2014W17",
"name": "Week 17 - 2014-04-21 - 2014-04-27",
+ "periodType": "WEEKLY",
"startDate": "2014-04-21",
},
Object {
+ "displayName": "Week 18 - 2014-04-28 - 2014-05-04",
"endDate": "2014-05-04",
"id": "2014W18",
"iso": "2014W18",
"name": "Week 18 - 2014-04-28 - 2014-05-04",
+ "periodType": "WEEKLY",
"startDate": "2014-04-28",
},
Object {
+ "displayName": "Week 19 - 2014-05-05 - 2014-05-11",
"endDate": "2014-05-11",
"id": "2014W19",
"iso": "2014W19",
"name": "Week 19 - 2014-05-05 - 2014-05-11",
+ "periodType": "WEEKLY",
"startDate": "2014-05-05",
},
Object {
+ "displayName": "Week 20 - 2014-05-12 - 2014-05-18",
"endDate": "2014-05-18",
"id": "2014W20",
"iso": "2014W20",
"name": "Week 20 - 2014-05-12 - 2014-05-18",
+ "periodType": "WEEKLY",
"startDate": "2014-05-12",
},
Object {
+ "displayName": "Week 21 - 2014-05-19 - 2014-05-25",
"endDate": "2014-05-25",
"id": "2014W21",
"iso": "2014W21",
"name": "Week 21 - 2014-05-19 - 2014-05-25",
+ "periodType": "WEEKLY",
"startDate": "2014-05-19",
},
Object {
+ "displayName": "Week 22 - 2014-05-26 - 2014-06-01",
"endDate": "2014-06-01",
"id": "2014W22",
"iso": "2014W22",
"name": "Week 22 - 2014-05-26 - 2014-06-01",
+ "periodType": "WEEKLY",
"startDate": "2014-05-26",
},
Object {
+ "displayName": "Week 23 - 2014-06-02 - 2014-06-08",
"endDate": "2014-06-08",
"id": "2014W23",
"iso": "2014W23",
"name": "Week 23 - 2014-06-02 - 2014-06-08",
+ "periodType": "WEEKLY",
"startDate": "2014-06-02",
},
Object {
+ "displayName": "Week 24 - 2014-06-09 - 2014-06-15",
"endDate": "2014-06-15",
"id": "2014W24",
"iso": "2014W24",
"name": "Week 24 - 2014-06-09 - 2014-06-15",
+ "periodType": "WEEKLY",
"startDate": "2014-06-09",
},
Object {
+ "displayName": "Week 25 - 2014-06-16 - 2014-06-22",
"endDate": "2014-06-22",
"id": "2014W25",
"iso": "2014W25",
"name": "Week 25 - 2014-06-16 - 2014-06-22",
+ "periodType": "WEEKLY",
"startDate": "2014-06-16",
},
Object {
+ "displayName": "Week 26 - 2014-06-23 - 2014-06-29",
"endDate": "2014-06-29",
"id": "2014W26",
"iso": "2014W26",
"name": "Week 26 - 2014-06-23 - 2014-06-29",
+ "periodType": "WEEKLY",
"startDate": "2014-06-23",
},
Object {
+ "displayName": "Week 27 - 2014-06-30 - 2014-07-06",
"endDate": "2014-07-06",
"id": "2014W27",
"iso": "2014W27",
"name": "Week 27 - 2014-06-30 - 2014-07-06",
+ "periodType": "WEEKLY",
"startDate": "2014-06-30",
},
Object {
+ "displayName": "Week 28 - 2014-07-07 - 2014-07-13",
"endDate": "2014-07-13",
"id": "2014W28",
"iso": "2014W28",
"name": "Week 28 - 2014-07-07 - 2014-07-13",
+ "periodType": "WEEKLY",
"startDate": "2014-07-07",
},
Object {
+ "displayName": "Week 29 - 2014-07-14 - 2014-07-20",
"endDate": "2014-07-20",
"id": "2014W29",
"iso": "2014W29",
"name": "Week 29 - 2014-07-14 - 2014-07-20",
+ "periodType": "WEEKLY",
"startDate": "2014-07-14",
},
Object {
+ "displayName": "Week 30 - 2014-07-21 - 2014-07-27",
"endDate": "2014-07-27",
"id": "2014W30",
"iso": "2014W30",
"name": "Week 30 - 2014-07-21 - 2014-07-27",
+ "periodType": "WEEKLY",
"startDate": "2014-07-21",
},
Object {
+ "displayName": "Week 31 - 2014-07-28 - 2014-08-03",
"endDate": "2014-08-03",
"id": "2014W31",
"iso": "2014W31",
"name": "Week 31 - 2014-07-28 - 2014-08-03",
+ "periodType": "WEEKLY",
"startDate": "2014-07-28",
},
Object {
+ "displayName": "Week 32 - 2014-08-04 - 2014-08-10",
"endDate": "2014-08-10",
"id": "2014W32",
"iso": "2014W32",
"name": "Week 32 - 2014-08-04 - 2014-08-10",
+ "periodType": "WEEKLY",
"startDate": "2014-08-04",
},
Object {
+ "displayName": "Week 33 - 2014-08-11 - 2014-08-17",
"endDate": "2014-08-17",
"id": "2014W33",
"iso": "2014W33",
"name": "Week 33 - 2014-08-11 - 2014-08-17",
+ "periodType": "WEEKLY",
"startDate": "2014-08-11",
},
Object {
+ "displayName": "Week 34 - 2014-08-18 - 2014-08-24",
"endDate": "2014-08-24",
"id": "2014W34",
"iso": "2014W34",
"name": "Week 34 - 2014-08-18 - 2014-08-24",
+ "periodType": "WEEKLY",
"startDate": "2014-08-18",
},
Object {
+ "displayName": "Week 35 - 2014-08-25 - 2014-08-31",
"endDate": "2014-08-31",
"id": "2014W35",
"iso": "2014W35",
"name": "Week 35 - 2014-08-25 - 2014-08-31",
+ "periodType": "WEEKLY",
"startDate": "2014-08-25",
},
Object {
+ "displayName": "Week 36 - 2014-09-01 - 2014-09-07",
"endDate": "2014-09-07",
"id": "2014W36",
"iso": "2014W36",
"name": "Week 36 - 2014-09-01 - 2014-09-07",
+ "periodType": "WEEKLY",
"startDate": "2014-09-01",
},
Object {
+ "displayName": "Week 37 - 2014-09-08 - 2014-09-14",
"endDate": "2014-09-14",
"id": "2014W37",
"iso": "2014W37",
"name": "Week 37 - 2014-09-08 - 2014-09-14",
+ "periodType": "WEEKLY",
"startDate": "2014-09-08",
},
Object {
+ "displayName": "Week 38 - 2014-09-15 - 2014-09-21",
"endDate": "2014-09-21",
"id": "2014W38",
"iso": "2014W38",
"name": "Week 38 - 2014-09-15 - 2014-09-21",
+ "periodType": "WEEKLY",
"startDate": "2014-09-15",
},
Object {
+ "displayName": "Week 39 - 2014-09-22 - 2014-09-28",
"endDate": "2014-09-28",
"id": "2014W39",
"iso": "2014W39",
"name": "Week 39 - 2014-09-22 - 2014-09-28",
+ "periodType": "WEEKLY",
"startDate": "2014-09-22",
},
Object {
+ "displayName": "Week 40 - 2014-09-29 - 2014-10-05",
"endDate": "2014-10-05",
"id": "2014W40",
"iso": "2014W40",
"name": "Week 40 - 2014-09-29 - 2014-10-05",
+ "periodType": "WEEKLY",
"startDate": "2014-09-29",
},
Object {
+ "displayName": "Week 41 - 2014-10-06 - 2014-10-12",
"endDate": "2014-10-12",
"id": "2014W41",
"iso": "2014W41",
"name": "Week 41 - 2014-10-06 - 2014-10-12",
+ "periodType": "WEEKLY",
"startDate": "2014-10-06",
},
Object {
+ "displayName": "Week 42 - 2014-10-13 - 2014-10-19",
"endDate": "2014-10-19",
"id": "2014W42",
"iso": "2014W42",
"name": "Week 42 - 2014-10-13 - 2014-10-19",
+ "periodType": "WEEKLY",
"startDate": "2014-10-13",
},
Object {
+ "displayName": "Week 43 - 2014-10-20 - 2014-10-26",
"endDate": "2014-10-26",
"id": "2014W43",
"iso": "2014W43",
"name": "Week 43 - 2014-10-20 - 2014-10-26",
+ "periodType": "WEEKLY",
"startDate": "2014-10-20",
},
Object {
+ "displayName": "Week 44 - 2014-10-27 - 2014-11-02",
"endDate": "2014-11-02",
"id": "2014W44",
"iso": "2014W44",
"name": "Week 44 - 2014-10-27 - 2014-11-02",
+ "periodType": "WEEKLY",
"startDate": "2014-10-27",
},
Object {
+ "displayName": "Week 45 - 2014-11-03 - 2014-11-09",
"endDate": "2014-11-09",
"id": "2014W45",
"iso": "2014W45",
"name": "Week 45 - 2014-11-03 - 2014-11-09",
+ "periodType": "WEEKLY",
"startDate": "2014-11-03",
},
Object {
+ "displayName": "Week 46 - 2014-11-10 - 2014-11-16",
"endDate": "2014-11-16",
"id": "2014W46",
"iso": "2014W46",
"name": "Week 46 - 2014-11-10 - 2014-11-16",
+ "periodType": "WEEKLY",
"startDate": "2014-11-10",
},
Object {
+ "displayName": "Week 47 - 2014-11-17 - 2014-11-23",
"endDate": "2014-11-23",
"id": "2014W47",
"iso": "2014W47",
"name": "Week 47 - 2014-11-17 - 2014-11-23",
+ "periodType": "WEEKLY",
"startDate": "2014-11-17",
},
Object {
+ "displayName": "Week 48 - 2014-11-24 - 2014-11-30",
"endDate": "2014-11-30",
"id": "2014W48",
"iso": "2014W48",
"name": "Week 48 - 2014-11-24 - 2014-11-30",
+ "periodType": "WEEKLY",
"startDate": "2014-11-24",
},
Object {
+ "displayName": "Week 49 - 2014-12-01 - 2014-12-07",
"endDate": "2014-12-07",
"id": "2014W49",
"iso": "2014W49",
"name": "Week 49 - 2014-12-01 - 2014-12-07",
+ "periodType": "WEEKLY",
"startDate": "2014-12-01",
},
Object {
+ "displayName": "Week 50 - 2014-12-08 - 2014-12-14",
"endDate": "2014-12-14",
"id": "2014W50",
"iso": "2014W50",
"name": "Week 50 - 2014-12-08 - 2014-12-14",
+ "periodType": "WEEKLY",
"startDate": "2014-12-08",
},
Object {
+ "displayName": "Week 51 - 2014-12-15 - 2014-12-21",
"endDate": "2014-12-21",
"id": "2014W51",
"iso": "2014W51",
"name": "Week 51 - 2014-12-15 - 2014-12-21",
+ "periodType": "WEEKLY",
"startDate": "2014-12-15",
},
Object {
+ "displayName": "Week 52 - 2014-12-22 - 2014-12-28",
"endDate": "2014-12-28",
"id": "2014W52",
"iso": "2014W52",
"name": "Week 52 - 2014-12-22 - 2014-12-28",
+ "periodType": "WEEKLY",
"startDate": "2014-12-22",
},
],
@@ -3649,367 +4707,471 @@ Object {
"name": "Weekly (Start Saturday)",
"options": Array [
Object {
+ "displayName": "Week 1 - 2014-01-04 - 2014-01-10",
"endDate": "2014-01-10",
"id": "2014SatW1",
"iso": "2014SatW1",
"name": "Week 1 - 2014-01-04 - 2014-01-10",
+ "periodType": "WEEKLY",
"startDate": "2014-01-04",
},
Object {
+ "displayName": "Week 2 - 2014-01-11 - 2014-01-17",
"endDate": "2014-01-17",
"id": "2014SatW2",
"iso": "2014SatW2",
"name": "Week 2 - 2014-01-11 - 2014-01-17",
+ "periodType": "WEEKLY",
"startDate": "2014-01-11",
},
Object {
+ "displayName": "Week 3 - 2014-01-18 - 2014-01-24",
"endDate": "2014-01-24",
"id": "2014SatW3",
"iso": "2014SatW3",
"name": "Week 3 - 2014-01-18 - 2014-01-24",
+ "periodType": "WEEKLY",
"startDate": "2014-01-18",
},
Object {
+ "displayName": "Week 4 - 2014-01-25 - 2014-01-31",
"endDate": "2014-01-31",
"id": "2014SatW4",
"iso": "2014SatW4",
"name": "Week 4 - 2014-01-25 - 2014-01-31",
+ "periodType": "WEEKLY",
"startDate": "2014-01-25",
},
Object {
+ "displayName": "Week 5 - 2014-02-01 - 2014-02-07",
"endDate": "2014-02-07",
"id": "2014SatW5",
"iso": "2014SatW5",
"name": "Week 5 - 2014-02-01 - 2014-02-07",
+ "periodType": "WEEKLY",
"startDate": "2014-02-01",
},
Object {
+ "displayName": "Week 6 - 2014-02-08 - 2014-02-14",
"endDate": "2014-02-14",
"id": "2014SatW6",
"iso": "2014SatW6",
"name": "Week 6 - 2014-02-08 - 2014-02-14",
+ "periodType": "WEEKLY",
"startDate": "2014-02-08",
},
Object {
+ "displayName": "Week 7 - 2014-02-15 - 2014-02-21",
"endDate": "2014-02-21",
"id": "2014SatW7",
"iso": "2014SatW7",
"name": "Week 7 - 2014-02-15 - 2014-02-21",
+ "periodType": "WEEKLY",
"startDate": "2014-02-15",
},
Object {
+ "displayName": "Week 8 - 2014-02-22 - 2014-02-28",
"endDate": "2014-02-28",
"id": "2014SatW8",
"iso": "2014SatW8",
"name": "Week 8 - 2014-02-22 - 2014-02-28",
+ "periodType": "WEEKLY",
"startDate": "2014-02-22",
},
Object {
+ "displayName": "Week 9 - 2014-03-01 - 2014-03-07",
"endDate": "2014-03-07",
"id": "2014SatW9",
"iso": "2014SatW9",
"name": "Week 9 - 2014-03-01 - 2014-03-07",
+ "periodType": "WEEKLY",
"startDate": "2014-03-01",
},
Object {
+ "displayName": "Week 10 - 2014-03-08 - 2014-03-14",
"endDate": "2014-03-14",
"id": "2014SatW10",
"iso": "2014SatW10",
"name": "Week 10 - 2014-03-08 - 2014-03-14",
+ "periodType": "WEEKLY",
"startDate": "2014-03-08",
},
Object {
+ "displayName": "Week 11 - 2014-03-15 - 2014-03-21",
"endDate": "2014-03-21",
"id": "2014SatW11",
"iso": "2014SatW11",
"name": "Week 11 - 2014-03-15 - 2014-03-21",
+ "periodType": "WEEKLY",
"startDate": "2014-03-15",
},
Object {
+ "displayName": "Week 12 - 2014-03-22 - 2014-03-28",
"endDate": "2014-03-28",
"id": "2014SatW12",
"iso": "2014SatW12",
"name": "Week 12 - 2014-03-22 - 2014-03-28",
+ "periodType": "WEEKLY",
"startDate": "2014-03-22",
},
Object {
+ "displayName": "Week 13 - 2014-03-29 - 2014-04-04",
"endDate": "2014-04-04",
"id": "2014SatW13",
"iso": "2014SatW13",
"name": "Week 13 - 2014-03-29 - 2014-04-04",
+ "periodType": "WEEKLY",
"startDate": "2014-03-29",
},
Object {
+ "displayName": "Week 14 - 2014-04-05 - 2014-04-11",
"endDate": "2014-04-11",
"id": "2014SatW14",
"iso": "2014SatW14",
"name": "Week 14 - 2014-04-05 - 2014-04-11",
+ "periodType": "WEEKLY",
"startDate": "2014-04-05",
},
Object {
+ "displayName": "Week 15 - 2014-04-12 - 2014-04-18",
"endDate": "2014-04-18",
"id": "2014SatW15",
"iso": "2014SatW15",
"name": "Week 15 - 2014-04-12 - 2014-04-18",
+ "periodType": "WEEKLY",
"startDate": "2014-04-12",
},
Object {
+ "displayName": "Week 16 - 2014-04-19 - 2014-04-25",
"endDate": "2014-04-25",
"id": "2014SatW16",
"iso": "2014SatW16",
"name": "Week 16 - 2014-04-19 - 2014-04-25",
+ "periodType": "WEEKLY",
"startDate": "2014-04-19",
},
Object {
+ "displayName": "Week 17 - 2014-04-26 - 2014-05-02",
"endDate": "2014-05-02",
"id": "2014SatW17",
"iso": "2014SatW17",
"name": "Week 17 - 2014-04-26 - 2014-05-02",
+ "periodType": "WEEKLY",
"startDate": "2014-04-26",
},
Object {
+ "displayName": "Week 18 - 2014-05-03 - 2014-05-09",
"endDate": "2014-05-09",
"id": "2014SatW18",
"iso": "2014SatW18",
"name": "Week 18 - 2014-05-03 - 2014-05-09",
+ "periodType": "WEEKLY",
"startDate": "2014-05-03",
},
Object {
+ "displayName": "Week 19 - 2014-05-10 - 2014-05-16",
"endDate": "2014-05-16",
"id": "2014SatW19",
"iso": "2014SatW19",
"name": "Week 19 - 2014-05-10 - 2014-05-16",
+ "periodType": "WEEKLY",
"startDate": "2014-05-10",
},
Object {
+ "displayName": "Week 20 - 2014-05-17 - 2014-05-23",
"endDate": "2014-05-23",
"id": "2014SatW20",
"iso": "2014SatW20",
"name": "Week 20 - 2014-05-17 - 2014-05-23",
+ "periodType": "WEEKLY",
"startDate": "2014-05-17",
},
Object {
+ "displayName": "Week 21 - 2014-05-24 - 2014-05-30",
"endDate": "2014-05-30",
"id": "2014SatW21",
"iso": "2014SatW21",
"name": "Week 21 - 2014-05-24 - 2014-05-30",
+ "periodType": "WEEKLY",
"startDate": "2014-05-24",
},
Object {
+ "displayName": "Week 22 - 2014-05-31 - 2014-06-06",
"endDate": "2014-06-06",
"id": "2014SatW22",
"iso": "2014SatW22",
"name": "Week 22 - 2014-05-31 - 2014-06-06",
+ "periodType": "WEEKLY",
"startDate": "2014-05-31",
},
Object {
+ "displayName": "Week 23 - 2014-06-07 - 2014-06-13",
"endDate": "2014-06-13",
"id": "2014SatW23",
"iso": "2014SatW23",
"name": "Week 23 - 2014-06-07 - 2014-06-13",
+ "periodType": "WEEKLY",
"startDate": "2014-06-07",
},
Object {
+ "displayName": "Week 24 - 2014-06-14 - 2014-06-20",
"endDate": "2014-06-20",
"id": "2014SatW24",
"iso": "2014SatW24",
"name": "Week 24 - 2014-06-14 - 2014-06-20",
+ "periodType": "WEEKLY",
"startDate": "2014-06-14",
},
Object {
+ "displayName": "Week 25 - 2014-06-21 - 2014-06-27",
"endDate": "2014-06-27",
"id": "2014SatW25",
"iso": "2014SatW25",
"name": "Week 25 - 2014-06-21 - 2014-06-27",
+ "periodType": "WEEKLY",
"startDate": "2014-06-21",
},
Object {
+ "displayName": "Week 26 - 2014-06-28 - 2014-07-04",
"endDate": "2014-07-04",
"id": "2014SatW26",
"iso": "2014SatW26",
"name": "Week 26 - 2014-06-28 - 2014-07-04",
+ "periodType": "WEEKLY",
"startDate": "2014-06-28",
},
Object {
+ "displayName": "Week 27 - 2014-07-05 - 2014-07-11",
"endDate": "2014-07-11",
"id": "2014SatW27",
"iso": "2014SatW27",
"name": "Week 27 - 2014-07-05 - 2014-07-11",
+ "periodType": "WEEKLY",
"startDate": "2014-07-05",
},
Object {
+ "displayName": "Week 28 - 2014-07-12 - 2014-07-18",
"endDate": "2014-07-18",
"id": "2014SatW28",
"iso": "2014SatW28",
"name": "Week 28 - 2014-07-12 - 2014-07-18",
+ "periodType": "WEEKLY",
"startDate": "2014-07-12",
},
Object {
+ "displayName": "Week 29 - 2014-07-19 - 2014-07-25",
"endDate": "2014-07-25",
"id": "2014SatW29",
"iso": "2014SatW29",
"name": "Week 29 - 2014-07-19 - 2014-07-25",
+ "periodType": "WEEKLY",
"startDate": "2014-07-19",
},
Object {
+ "displayName": "Week 30 - 2014-07-26 - 2014-08-01",
"endDate": "2014-08-01",
"id": "2014SatW30",
"iso": "2014SatW30",
"name": "Week 30 - 2014-07-26 - 2014-08-01",
+ "periodType": "WEEKLY",
"startDate": "2014-07-26",
},
Object {
+ "displayName": "Week 31 - 2014-08-02 - 2014-08-08",
"endDate": "2014-08-08",
"id": "2014SatW31",
"iso": "2014SatW31",
"name": "Week 31 - 2014-08-02 - 2014-08-08",
+ "periodType": "WEEKLY",
"startDate": "2014-08-02",
},
Object {
+ "displayName": "Week 32 - 2014-08-09 - 2014-08-15",
"endDate": "2014-08-15",
"id": "2014SatW32",
"iso": "2014SatW32",
"name": "Week 32 - 2014-08-09 - 2014-08-15",
+ "periodType": "WEEKLY",
"startDate": "2014-08-09",
},
Object {
+ "displayName": "Week 33 - 2014-08-16 - 2014-08-22",
"endDate": "2014-08-22",
"id": "2014SatW33",
"iso": "2014SatW33",
"name": "Week 33 - 2014-08-16 - 2014-08-22",
+ "periodType": "WEEKLY",
"startDate": "2014-08-16",
},
Object {
+ "displayName": "Week 34 - 2014-08-23 - 2014-08-29",
"endDate": "2014-08-29",
"id": "2014SatW34",
"iso": "2014SatW34",
"name": "Week 34 - 2014-08-23 - 2014-08-29",
+ "periodType": "WEEKLY",
"startDate": "2014-08-23",
},
Object {
+ "displayName": "Week 35 - 2014-08-30 - 2014-09-05",
"endDate": "2014-09-05",
"id": "2014SatW35",
"iso": "2014SatW35",
"name": "Week 35 - 2014-08-30 - 2014-09-05",
+ "periodType": "WEEKLY",
"startDate": "2014-08-30",
},
Object {
+ "displayName": "Week 36 - 2014-09-06 - 2014-09-12",
"endDate": "2014-09-12",
"id": "2014SatW36",
"iso": "2014SatW36",
"name": "Week 36 - 2014-09-06 - 2014-09-12",
+ "periodType": "WEEKLY",
"startDate": "2014-09-06",
},
Object {
+ "displayName": "Week 37 - 2014-09-13 - 2014-09-19",
"endDate": "2014-09-19",
"id": "2014SatW37",
"iso": "2014SatW37",
"name": "Week 37 - 2014-09-13 - 2014-09-19",
+ "periodType": "WEEKLY",
"startDate": "2014-09-13",
},
Object {
+ "displayName": "Week 38 - 2014-09-20 - 2014-09-26",
"endDate": "2014-09-26",
"id": "2014SatW38",
"iso": "2014SatW38",
"name": "Week 38 - 2014-09-20 - 2014-09-26",
+ "periodType": "WEEKLY",
"startDate": "2014-09-20",
},
Object {
+ "displayName": "Week 39 - 2014-09-27 - 2014-10-03",
"endDate": "2014-10-03",
"id": "2014SatW39",
"iso": "2014SatW39",
"name": "Week 39 - 2014-09-27 - 2014-10-03",
+ "periodType": "WEEKLY",
"startDate": "2014-09-27",
},
Object {
+ "displayName": "Week 40 - 2014-10-04 - 2014-10-10",
"endDate": "2014-10-10",
"id": "2014SatW40",
"iso": "2014SatW40",
"name": "Week 40 - 2014-10-04 - 2014-10-10",
+ "periodType": "WEEKLY",
"startDate": "2014-10-04",
},
Object {
+ "displayName": "Week 41 - 2014-10-11 - 2014-10-17",
"endDate": "2014-10-17",
"id": "2014SatW41",
"iso": "2014SatW41",
"name": "Week 41 - 2014-10-11 - 2014-10-17",
+ "periodType": "WEEKLY",
"startDate": "2014-10-11",
},
Object {
+ "displayName": "Week 42 - 2014-10-18 - 2014-10-24",
"endDate": "2014-10-24",
"id": "2014SatW42",
"iso": "2014SatW42",
"name": "Week 42 - 2014-10-18 - 2014-10-24",
+ "periodType": "WEEKLY",
"startDate": "2014-10-18",
},
Object {
+ "displayName": "Week 43 - 2014-10-25 - 2014-10-31",
"endDate": "2014-10-31",
"id": "2014SatW43",
"iso": "2014SatW43",
"name": "Week 43 - 2014-10-25 - 2014-10-31",
+ "periodType": "WEEKLY",
"startDate": "2014-10-25",
},
Object {
+ "displayName": "Week 44 - 2014-11-01 - 2014-11-07",
"endDate": "2014-11-07",
"id": "2014SatW44",
"iso": "2014SatW44",
"name": "Week 44 - 2014-11-01 - 2014-11-07",
+ "periodType": "WEEKLY",
"startDate": "2014-11-01",
},
Object {
+ "displayName": "Week 45 - 2014-11-08 - 2014-11-14",
"endDate": "2014-11-14",
"id": "2014SatW45",
"iso": "2014SatW45",
"name": "Week 45 - 2014-11-08 - 2014-11-14",
+ "periodType": "WEEKLY",
"startDate": "2014-11-08",
},
Object {
+ "displayName": "Week 46 - 2014-11-15 - 2014-11-21",
"endDate": "2014-11-21",
"id": "2014SatW46",
"iso": "2014SatW46",
"name": "Week 46 - 2014-11-15 - 2014-11-21",
+ "periodType": "WEEKLY",
"startDate": "2014-11-15",
},
Object {
+ "displayName": "Week 47 - 2014-11-22 - 2014-11-28",
"endDate": "2014-11-28",
"id": "2014SatW47",
"iso": "2014SatW47",
"name": "Week 47 - 2014-11-22 - 2014-11-28",
+ "periodType": "WEEKLY",
"startDate": "2014-11-22",
},
Object {
+ "displayName": "Week 48 - 2014-11-29 - 2014-12-05",
"endDate": "2014-12-05",
"id": "2014SatW48",
"iso": "2014SatW48",
"name": "Week 48 - 2014-11-29 - 2014-12-05",
+ "periodType": "WEEKLY",
"startDate": "2014-11-29",
},
Object {
+ "displayName": "Week 49 - 2014-12-06 - 2014-12-12",
"endDate": "2014-12-12",
"id": "2014SatW49",
"iso": "2014SatW49",
"name": "Week 49 - 2014-12-06 - 2014-12-12",
+ "periodType": "WEEKLY",
"startDate": "2014-12-06",
},
Object {
+ "displayName": "Week 50 - 2014-12-13 - 2014-12-19",
"endDate": "2014-12-19",
"id": "2014SatW50",
"iso": "2014SatW50",
"name": "Week 50 - 2014-12-13 - 2014-12-19",
+ "periodType": "WEEKLY",
"startDate": "2014-12-13",
},
Object {
+ "displayName": "Week 51 - 2014-12-20 - 2014-12-26",
"endDate": "2014-12-26",
"id": "2014SatW51",
"iso": "2014SatW51",
"name": "Week 51 - 2014-12-20 - 2014-12-26",
+ "periodType": "WEEKLY",
"startDate": "2014-12-20",
},
Object {
+ "displayName": "Week 52 - 2014-12-27 - 2015-01-02",
"endDate": "2015-01-02",
"id": "2014SatW52",
"iso": "2014SatW52",
"name": "Week 52 - 2014-12-27 - 2015-01-02",
+ "periodType": "WEEKLY",
"startDate": "2014-12-27",
},
],
@@ -4023,374 +5185,480 @@ Object {
"name": "Weekly (Start Sunday)",
"options": Array [
Object {
+ "displayName": "Week 1 - 2013-12-29 - 2014-01-04",
"endDate": "2014-01-04",
"id": "2014SunW1",
"iso": "2014SunW1",
"name": "Week 1 - 2013-12-29 - 2014-01-04",
+ "periodType": "WEEKLY",
"startDate": "2013-12-29",
},
Object {
+ "displayName": "Week 2 - 2014-01-05 - 2014-01-11",
"endDate": "2014-01-11",
"id": "2014SunW2",
"iso": "2014SunW2",
"name": "Week 2 - 2014-01-05 - 2014-01-11",
+ "periodType": "WEEKLY",
"startDate": "2014-01-05",
},
Object {
+ "displayName": "Week 3 - 2014-01-12 - 2014-01-18",
"endDate": "2014-01-18",
"id": "2014SunW3",
"iso": "2014SunW3",
"name": "Week 3 - 2014-01-12 - 2014-01-18",
+ "periodType": "WEEKLY",
"startDate": "2014-01-12",
},
Object {
+ "displayName": "Week 4 - 2014-01-19 - 2014-01-25",
"endDate": "2014-01-25",
"id": "2014SunW4",
"iso": "2014SunW4",
"name": "Week 4 - 2014-01-19 - 2014-01-25",
+ "periodType": "WEEKLY",
"startDate": "2014-01-19",
},
Object {
+ "displayName": "Week 5 - 2014-01-26 - 2014-02-01",
"endDate": "2014-02-01",
"id": "2014SunW5",
"iso": "2014SunW5",
"name": "Week 5 - 2014-01-26 - 2014-02-01",
+ "periodType": "WEEKLY",
"startDate": "2014-01-26",
},
Object {
+ "displayName": "Week 6 - 2014-02-02 - 2014-02-08",
"endDate": "2014-02-08",
"id": "2014SunW6",
"iso": "2014SunW6",
"name": "Week 6 - 2014-02-02 - 2014-02-08",
+ "periodType": "WEEKLY",
"startDate": "2014-02-02",
},
Object {
+ "displayName": "Week 7 - 2014-02-09 - 2014-02-15",
"endDate": "2014-02-15",
"id": "2014SunW7",
"iso": "2014SunW7",
"name": "Week 7 - 2014-02-09 - 2014-02-15",
+ "periodType": "WEEKLY",
"startDate": "2014-02-09",
},
Object {
+ "displayName": "Week 8 - 2014-02-16 - 2014-02-22",
"endDate": "2014-02-22",
"id": "2014SunW8",
"iso": "2014SunW8",
"name": "Week 8 - 2014-02-16 - 2014-02-22",
+ "periodType": "WEEKLY",
"startDate": "2014-02-16",
},
Object {
+ "displayName": "Week 9 - 2014-02-23 - 2014-03-01",
"endDate": "2014-03-01",
"id": "2014SunW9",
"iso": "2014SunW9",
"name": "Week 9 - 2014-02-23 - 2014-03-01",
+ "periodType": "WEEKLY",
"startDate": "2014-02-23",
},
Object {
+ "displayName": "Week 10 - 2014-03-02 - 2014-03-08",
"endDate": "2014-03-08",
"id": "2014SunW10",
"iso": "2014SunW10",
"name": "Week 10 - 2014-03-02 - 2014-03-08",
+ "periodType": "WEEKLY",
"startDate": "2014-03-02",
},
Object {
+ "displayName": "Week 11 - 2014-03-09 - 2014-03-15",
"endDate": "2014-03-15",
"id": "2014SunW11",
"iso": "2014SunW11",
"name": "Week 11 - 2014-03-09 - 2014-03-15",
+ "periodType": "WEEKLY",
"startDate": "2014-03-09",
},
Object {
+ "displayName": "Week 12 - 2014-03-16 - 2014-03-22",
"endDate": "2014-03-22",
"id": "2014SunW12",
"iso": "2014SunW12",
"name": "Week 12 - 2014-03-16 - 2014-03-22",
+ "periodType": "WEEKLY",
"startDate": "2014-03-16",
},
Object {
+ "displayName": "Week 13 - 2014-03-23 - 2014-03-29",
"endDate": "2014-03-29",
"id": "2014SunW13",
"iso": "2014SunW13",
"name": "Week 13 - 2014-03-23 - 2014-03-29",
+ "periodType": "WEEKLY",
"startDate": "2014-03-23",
},
Object {
+ "displayName": "Week 14 - 2014-03-30 - 2014-04-05",
"endDate": "2014-04-05",
"id": "2014SunW14",
"iso": "2014SunW14",
"name": "Week 14 - 2014-03-30 - 2014-04-05",
+ "periodType": "WEEKLY",
"startDate": "2014-03-30",
},
Object {
+ "displayName": "Week 15 - 2014-04-06 - 2014-04-12",
"endDate": "2014-04-12",
"id": "2014SunW15",
"iso": "2014SunW15",
"name": "Week 15 - 2014-04-06 - 2014-04-12",
+ "periodType": "WEEKLY",
"startDate": "2014-04-06",
},
Object {
+ "displayName": "Week 16 - 2014-04-13 - 2014-04-19",
"endDate": "2014-04-19",
"id": "2014SunW16",
"iso": "2014SunW16",
"name": "Week 16 - 2014-04-13 - 2014-04-19",
+ "periodType": "WEEKLY",
"startDate": "2014-04-13",
},
Object {
+ "displayName": "Week 17 - 2014-04-20 - 2014-04-26",
"endDate": "2014-04-26",
"id": "2014SunW17",
"iso": "2014SunW17",
"name": "Week 17 - 2014-04-20 - 2014-04-26",
+ "periodType": "WEEKLY",
"startDate": "2014-04-20",
},
Object {
+ "displayName": "Week 18 - 2014-04-27 - 2014-05-03",
"endDate": "2014-05-03",
"id": "2014SunW18",
"iso": "2014SunW18",
"name": "Week 18 - 2014-04-27 - 2014-05-03",
+ "periodType": "WEEKLY",
"startDate": "2014-04-27",
},
Object {
+ "displayName": "Week 19 - 2014-05-04 - 2014-05-10",
"endDate": "2014-05-10",
"id": "2014SunW19",
"iso": "2014SunW19",
"name": "Week 19 - 2014-05-04 - 2014-05-10",
+ "periodType": "WEEKLY",
"startDate": "2014-05-04",
},
Object {
+ "displayName": "Week 20 - 2014-05-11 - 2014-05-17",
"endDate": "2014-05-17",
"id": "2014SunW20",
"iso": "2014SunW20",
"name": "Week 20 - 2014-05-11 - 2014-05-17",
+ "periodType": "WEEKLY",
"startDate": "2014-05-11",
},
Object {
+ "displayName": "Week 21 - 2014-05-18 - 2014-05-24",
"endDate": "2014-05-24",
"id": "2014SunW21",
"iso": "2014SunW21",
"name": "Week 21 - 2014-05-18 - 2014-05-24",
+ "periodType": "WEEKLY",
"startDate": "2014-05-18",
},
Object {
+ "displayName": "Week 22 - 2014-05-25 - 2014-05-31",
"endDate": "2014-05-31",
"id": "2014SunW22",
"iso": "2014SunW22",
"name": "Week 22 - 2014-05-25 - 2014-05-31",
+ "periodType": "WEEKLY",
"startDate": "2014-05-25",
},
Object {
+ "displayName": "Week 23 - 2014-06-01 - 2014-06-07",
"endDate": "2014-06-07",
"id": "2014SunW23",
"iso": "2014SunW23",
"name": "Week 23 - 2014-06-01 - 2014-06-07",
+ "periodType": "WEEKLY",
"startDate": "2014-06-01",
},
Object {
+ "displayName": "Week 24 - 2014-06-08 - 2014-06-14",
"endDate": "2014-06-14",
"id": "2014SunW24",
"iso": "2014SunW24",
"name": "Week 24 - 2014-06-08 - 2014-06-14",
+ "periodType": "WEEKLY",
"startDate": "2014-06-08",
},
Object {
+ "displayName": "Week 25 - 2014-06-15 - 2014-06-21",
"endDate": "2014-06-21",
"id": "2014SunW25",
"iso": "2014SunW25",
"name": "Week 25 - 2014-06-15 - 2014-06-21",
+ "periodType": "WEEKLY",
"startDate": "2014-06-15",
},
Object {
+ "displayName": "Week 26 - 2014-06-22 - 2014-06-28",
"endDate": "2014-06-28",
"id": "2014SunW26",
"iso": "2014SunW26",
"name": "Week 26 - 2014-06-22 - 2014-06-28",
+ "periodType": "WEEKLY",
"startDate": "2014-06-22",
},
Object {
+ "displayName": "Week 27 - 2014-06-29 - 2014-07-05",
"endDate": "2014-07-05",
"id": "2014SunW27",
"iso": "2014SunW27",
"name": "Week 27 - 2014-06-29 - 2014-07-05",
+ "periodType": "WEEKLY",
"startDate": "2014-06-29",
},
Object {
+ "displayName": "Week 28 - 2014-07-06 - 2014-07-12",
"endDate": "2014-07-12",
"id": "2014SunW28",
"iso": "2014SunW28",
"name": "Week 28 - 2014-07-06 - 2014-07-12",
+ "periodType": "WEEKLY",
"startDate": "2014-07-06",
},
Object {
+ "displayName": "Week 29 - 2014-07-13 - 2014-07-19",
"endDate": "2014-07-19",
"id": "2014SunW29",
"iso": "2014SunW29",
"name": "Week 29 - 2014-07-13 - 2014-07-19",
+ "periodType": "WEEKLY",
"startDate": "2014-07-13",
},
Object {
+ "displayName": "Week 30 - 2014-07-20 - 2014-07-26",
"endDate": "2014-07-26",
"id": "2014SunW30",
"iso": "2014SunW30",
"name": "Week 30 - 2014-07-20 - 2014-07-26",
+ "periodType": "WEEKLY",
"startDate": "2014-07-20",
},
Object {
+ "displayName": "Week 31 - 2014-07-27 - 2014-08-02",
"endDate": "2014-08-02",
"id": "2014SunW31",
"iso": "2014SunW31",
"name": "Week 31 - 2014-07-27 - 2014-08-02",
+ "periodType": "WEEKLY",
"startDate": "2014-07-27",
},
Object {
+ "displayName": "Week 32 - 2014-08-03 - 2014-08-09",
"endDate": "2014-08-09",
"id": "2014SunW32",
"iso": "2014SunW32",
"name": "Week 32 - 2014-08-03 - 2014-08-09",
+ "periodType": "WEEKLY",
"startDate": "2014-08-03",
},
Object {
+ "displayName": "Week 33 - 2014-08-10 - 2014-08-16",
"endDate": "2014-08-16",
"id": "2014SunW33",
"iso": "2014SunW33",
"name": "Week 33 - 2014-08-10 - 2014-08-16",
+ "periodType": "WEEKLY",
"startDate": "2014-08-10",
},
Object {
+ "displayName": "Week 34 - 2014-08-17 - 2014-08-23",
"endDate": "2014-08-23",
"id": "2014SunW34",
"iso": "2014SunW34",
"name": "Week 34 - 2014-08-17 - 2014-08-23",
+ "periodType": "WEEKLY",
"startDate": "2014-08-17",
},
Object {
+ "displayName": "Week 35 - 2014-08-24 - 2014-08-30",
"endDate": "2014-08-30",
"id": "2014SunW35",
"iso": "2014SunW35",
"name": "Week 35 - 2014-08-24 - 2014-08-30",
+ "periodType": "WEEKLY",
"startDate": "2014-08-24",
},
Object {
+ "displayName": "Week 36 - 2014-08-31 - 2014-09-06",
"endDate": "2014-09-06",
"id": "2014SunW36",
"iso": "2014SunW36",
"name": "Week 36 - 2014-08-31 - 2014-09-06",
+ "periodType": "WEEKLY",
"startDate": "2014-08-31",
},
Object {
+ "displayName": "Week 37 - 2014-09-07 - 2014-09-13",
"endDate": "2014-09-13",
"id": "2014SunW37",
"iso": "2014SunW37",
"name": "Week 37 - 2014-09-07 - 2014-09-13",
+ "periodType": "WEEKLY",
"startDate": "2014-09-07",
},
Object {
+ "displayName": "Week 38 - 2014-09-14 - 2014-09-20",
"endDate": "2014-09-20",
"id": "2014SunW38",
"iso": "2014SunW38",
"name": "Week 38 - 2014-09-14 - 2014-09-20",
+ "periodType": "WEEKLY",
"startDate": "2014-09-14",
},
Object {
+ "displayName": "Week 39 - 2014-09-21 - 2014-09-27",
"endDate": "2014-09-27",
"id": "2014SunW39",
"iso": "2014SunW39",
"name": "Week 39 - 2014-09-21 - 2014-09-27",
+ "periodType": "WEEKLY",
"startDate": "2014-09-21",
},
Object {
+ "displayName": "Week 40 - 2014-09-28 - 2014-10-04",
"endDate": "2014-10-04",
"id": "2014SunW40",
"iso": "2014SunW40",
"name": "Week 40 - 2014-09-28 - 2014-10-04",
+ "periodType": "WEEKLY",
"startDate": "2014-09-28",
},
Object {
+ "displayName": "Week 41 - 2014-10-05 - 2014-10-11",
"endDate": "2014-10-11",
"id": "2014SunW41",
"iso": "2014SunW41",
"name": "Week 41 - 2014-10-05 - 2014-10-11",
+ "periodType": "WEEKLY",
"startDate": "2014-10-05",
},
Object {
+ "displayName": "Week 42 - 2014-10-12 - 2014-10-18",
"endDate": "2014-10-18",
"id": "2014SunW42",
"iso": "2014SunW42",
"name": "Week 42 - 2014-10-12 - 2014-10-18",
+ "periodType": "WEEKLY",
"startDate": "2014-10-12",
},
Object {
+ "displayName": "Week 43 - 2014-10-19 - 2014-10-25",
"endDate": "2014-10-25",
"id": "2014SunW43",
"iso": "2014SunW43",
"name": "Week 43 - 2014-10-19 - 2014-10-25",
+ "periodType": "WEEKLY",
"startDate": "2014-10-19",
},
Object {
+ "displayName": "Week 44 - 2014-10-26 - 2014-11-01",
"endDate": "2014-11-01",
"id": "2014SunW44",
"iso": "2014SunW44",
"name": "Week 44 - 2014-10-26 - 2014-11-01",
+ "periodType": "WEEKLY",
"startDate": "2014-10-26",
},
Object {
+ "displayName": "Week 45 - 2014-11-02 - 2014-11-08",
"endDate": "2014-11-08",
"id": "2014SunW45",
"iso": "2014SunW45",
"name": "Week 45 - 2014-11-02 - 2014-11-08",
+ "periodType": "WEEKLY",
"startDate": "2014-11-02",
},
Object {
+ "displayName": "Week 46 - 2014-11-09 - 2014-11-15",
"endDate": "2014-11-15",
"id": "2014SunW46",
"iso": "2014SunW46",
"name": "Week 46 - 2014-11-09 - 2014-11-15",
+ "periodType": "WEEKLY",
"startDate": "2014-11-09",
},
Object {
+ "displayName": "Week 47 - 2014-11-16 - 2014-11-22",
"endDate": "2014-11-22",
"id": "2014SunW47",
"iso": "2014SunW47",
"name": "Week 47 - 2014-11-16 - 2014-11-22",
+ "periodType": "WEEKLY",
"startDate": "2014-11-16",
},
Object {
+ "displayName": "Week 48 - 2014-11-23 - 2014-11-29",
"endDate": "2014-11-29",
"id": "2014SunW48",
"iso": "2014SunW48",
"name": "Week 48 - 2014-11-23 - 2014-11-29",
+ "periodType": "WEEKLY",
"startDate": "2014-11-23",
},
Object {
+ "displayName": "Week 49 - 2014-11-30 - 2014-12-06",
"endDate": "2014-12-06",
"id": "2014SunW49",
"iso": "2014SunW49",
"name": "Week 49 - 2014-11-30 - 2014-12-06",
+ "periodType": "WEEKLY",
"startDate": "2014-11-30",
},
Object {
+ "displayName": "Week 50 - 2014-12-07 - 2014-12-13",
"endDate": "2014-12-13",
"id": "2014SunW50",
"iso": "2014SunW50",
"name": "Week 50 - 2014-12-07 - 2014-12-13",
+ "periodType": "WEEKLY",
"startDate": "2014-12-07",
},
Object {
+ "displayName": "Week 51 - 2014-12-14 - 2014-12-20",
"endDate": "2014-12-20",
"id": "2014SunW51",
"iso": "2014SunW51",
"name": "Week 51 - 2014-12-14 - 2014-12-20",
+ "periodType": "WEEKLY",
"startDate": "2014-12-14",
},
Object {
+ "displayName": "Week 52 - 2014-12-21 - 2014-12-27",
"endDate": "2014-12-27",
"id": "2014SunW52",
"iso": "2014SunW52",
"name": "Week 52 - 2014-12-21 - 2014-12-27",
+ "periodType": "WEEKLY",
"startDate": "2014-12-21",
},
Object {
+ "displayName": "Week 53 - 2014-12-28 - 2015-01-03",
"endDate": "2015-01-03",
"id": "2014SunW53",
"iso": "2014SunW53",
"name": "Week 53 - 2014-12-28 - 2015-01-03",
+ "periodType": "WEEKLY",
"startDate": "2014-12-28",
},
],
@@ -4404,374 +5672,480 @@ Object {
"name": "Weekly (Start Sunday)",
"options": Array [
Object {
+ "displayName": "Week 1 - 2013-12-29 - 2014-01-04",
"endDate": "2014-01-04",
"id": "2014SunW1",
"iso": "2014SunW1",
"name": "Week 1 - 2013-12-29 - 2014-01-04",
+ "periodType": "WEEKLY",
"startDate": "2013-12-29",
},
Object {
+ "displayName": "Week 2 - 2014-01-05 - 2014-01-11",
"endDate": "2014-01-11",
"id": "2014SunW2",
"iso": "2014SunW2",
"name": "Week 2 - 2014-01-05 - 2014-01-11",
+ "periodType": "WEEKLY",
"startDate": "2014-01-05",
},
Object {
+ "displayName": "Week 3 - 2014-01-12 - 2014-01-18",
"endDate": "2014-01-18",
"id": "2014SunW3",
"iso": "2014SunW3",
"name": "Week 3 - 2014-01-12 - 2014-01-18",
+ "periodType": "WEEKLY",
"startDate": "2014-01-12",
},
Object {
+ "displayName": "Week 4 - 2014-01-19 - 2014-01-25",
"endDate": "2014-01-25",
"id": "2014SunW4",
"iso": "2014SunW4",
"name": "Week 4 - 2014-01-19 - 2014-01-25",
+ "periodType": "WEEKLY",
"startDate": "2014-01-19",
},
Object {
+ "displayName": "Week 5 - 2014-01-26 - 2014-02-01",
"endDate": "2014-02-01",
"id": "2014SunW5",
"iso": "2014SunW5",
"name": "Week 5 - 2014-01-26 - 2014-02-01",
+ "periodType": "WEEKLY",
"startDate": "2014-01-26",
},
Object {
+ "displayName": "Week 6 - 2014-02-02 - 2014-02-08",
"endDate": "2014-02-08",
"id": "2014SunW6",
"iso": "2014SunW6",
"name": "Week 6 - 2014-02-02 - 2014-02-08",
+ "periodType": "WEEKLY",
"startDate": "2014-02-02",
},
Object {
+ "displayName": "Week 7 - 2014-02-09 - 2014-02-15",
"endDate": "2014-02-15",
"id": "2014SunW7",
"iso": "2014SunW7",
"name": "Week 7 - 2014-02-09 - 2014-02-15",
+ "periodType": "WEEKLY",
"startDate": "2014-02-09",
},
Object {
+ "displayName": "Week 8 - 2014-02-16 - 2014-02-22",
"endDate": "2014-02-22",
"id": "2014SunW8",
"iso": "2014SunW8",
"name": "Week 8 - 2014-02-16 - 2014-02-22",
+ "periodType": "WEEKLY",
"startDate": "2014-02-16",
},
Object {
+ "displayName": "Week 9 - 2014-02-23 - 2014-03-01",
"endDate": "2014-03-01",
"id": "2014SunW9",
"iso": "2014SunW9",
"name": "Week 9 - 2014-02-23 - 2014-03-01",
+ "periodType": "WEEKLY",
"startDate": "2014-02-23",
},
Object {
+ "displayName": "Week 10 - 2014-03-02 - 2014-03-08",
"endDate": "2014-03-08",
"id": "2014SunW10",
"iso": "2014SunW10",
"name": "Week 10 - 2014-03-02 - 2014-03-08",
+ "periodType": "WEEKLY",
"startDate": "2014-03-02",
},
Object {
+ "displayName": "Week 11 - 2014-03-09 - 2014-03-15",
"endDate": "2014-03-15",
"id": "2014SunW11",
"iso": "2014SunW11",
"name": "Week 11 - 2014-03-09 - 2014-03-15",
+ "periodType": "WEEKLY",
"startDate": "2014-03-09",
},
Object {
+ "displayName": "Week 12 - 2014-03-16 - 2014-03-22",
"endDate": "2014-03-22",
"id": "2014SunW12",
"iso": "2014SunW12",
"name": "Week 12 - 2014-03-16 - 2014-03-22",
+ "periodType": "WEEKLY",
"startDate": "2014-03-16",
},
Object {
+ "displayName": "Week 13 - 2014-03-23 - 2014-03-29",
"endDate": "2014-03-29",
"id": "2014SunW13",
"iso": "2014SunW13",
"name": "Week 13 - 2014-03-23 - 2014-03-29",
+ "periodType": "WEEKLY",
"startDate": "2014-03-23",
},
Object {
+ "displayName": "Week 14 - 2014-03-30 - 2014-04-05",
"endDate": "2014-04-05",
"id": "2014SunW14",
"iso": "2014SunW14",
"name": "Week 14 - 2014-03-30 - 2014-04-05",
+ "periodType": "WEEKLY",
"startDate": "2014-03-30",
},
Object {
+ "displayName": "Week 15 - 2014-04-06 - 2014-04-12",
"endDate": "2014-04-12",
"id": "2014SunW15",
"iso": "2014SunW15",
"name": "Week 15 - 2014-04-06 - 2014-04-12",
+ "periodType": "WEEKLY",
"startDate": "2014-04-06",
},
Object {
+ "displayName": "Week 16 - 2014-04-13 - 2014-04-19",
"endDate": "2014-04-19",
"id": "2014SunW16",
"iso": "2014SunW16",
"name": "Week 16 - 2014-04-13 - 2014-04-19",
+ "periodType": "WEEKLY",
"startDate": "2014-04-13",
},
Object {
+ "displayName": "Week 17 - 2014-04-20 - 2014-04-26",
"endDate": "2014-04-26",
"id": "2014SunW17",
"iso": "2014SunW17",
"name": "Week 17 - 2014-04-20 - 2014-04-26",
+ "periodType": "WEEKLY",
"startDate": "2014-04-20",
},
Object {
+ "displayName": "Week 18 - 2014-04-27 - 2014-05-03",
"endDate": "2014-05-03",
"id": "2014SunW18",
"iso": "2014SunW18",
"name": "Week 18 - 2014-04-27 - 2014-05-03",
+ "periodType": "WEEKLY",
"startDate": "2014-04-27",
},
Object {
+ "displayName": "Week 19 - 2014-05-04 - 2014-05-10",
"endDate": "2014-05-10",
"id": "2014SunW19",
"iso": "2014SunW19",
"name": "Week 19 - 2014-05-04 - 2014-05-10",
+ "periodType": "WEEKLY",
"startDate": "2014-05-04",
},
Object {
+ "displayName": "Week 20 - 2014-05-11 - 2014-05-17",
"endDate": "2014-05-17",
"id": "2014SunW20",
"iso": "2014SunW20",
"name": "Week 20 - 2014-05-11 - 2014-05-17",
+ "periodType": "WEEKLY",
"startDate": "2014-05-11",
},
Object {
+ "displayName": "Week 21 - 2014-05-18 - 2014-05-24",
"endDate": "2014-05-24",
"id": "2014SunW21",
"iso": "2014SunW21",
"name": "Week 21 - 2014-05-18 - 2014-05-24",
+ "periodType": "WEEKLY",
"startDate": "2014-05-18",
},
Object {
+ "displayName": "Week 22 - 2014-05-25 - 2014-05-31",
"endDate": "2014-05-31",
"id": "2014SunW22",
"iso": "2014SunW22",
"name": "Week 22 - 2014-05-25 - 2014-05-31",
+ "periodType": "WEEKLY",
"startDate": "2014-05-25",
},
Object {
+ "displayName": "Week 23 - 2014-06-01 - 2014-06-07",
"endDate": "2014-06-07",
"id": "2014SunW23",
"iso": "2014SunW23",
"name": "Week 23 - 2014-06-01 - 2014-06-07",
+ "periodType": "WEEKLY",
"startDate": "2014-06-01",
},
Object {
+ "displayName": "Week 24 - 2014-06-08 - 2014-06-14",
"endDate": "2014-06-14",
"id": "2014SunW24",
"iso": "2014SunW24",
"name": "Week 24 - 2014-06-08 - 2014-06-14",
+ "periodType": "WEEKLY",
"startDate": "2014-06-08",
},
Object {
+ "displayName": "Week 25 - 2014-06-15 - 2014-06-21",
"endDate": "2014-06-21",
"id": "2014SunW25",
"iso": "2014SunW25",
"name": "Week 25 - 2014-06-15 - 2014-06-21",
+ "periodType": "WEEKLY",
"startDate": "2014-06-15",
},
Object {
+ "displayName": "Week 26 - 2014-06-22 - 2014-06-28",
"endDate": "2014-06-28",
"id": "2014SunW26",
"iso": "2014SunW26",
"name": "Week 26 - 2014-06-22 - 2014-06-28",
+ "periodType": "WEEKLY",
"startDate": "2014-06-22",
},
Object {
+ "displayName": "Week 27 - 2014-06-29 - 2014-07-05",
"endDate": "2014-07-05",
"id": "2014SunW27",
"iso": "2014SunW27",
"name": "Week 27 - 2014-06-29 - 2014-07-05",
+ "periodType": "WEEKLY",
"startDate": "2014-06-29",
},
Object {
+ "displayName": "Week 28 - 2014-07-06 - 2014-07-12",
"endDate": "2014-07-12",
"id": "2014SunW28",
"iso": "2014SunW28",
"name": "Week 28 - 2014-07-06 - 2014-07-12",
+ "periodType": "WEEKLY",
"startDate": "2014-07-06",
},
Object {
+ "displayName": "Week 29 - 2014-07-13 - 2014-07-19",
"endDate": "2014-07-19",
"id": "2014SunW29",
"iso": "2014SunW29",
"name": "Week 29 - 2014-07-13 - 2014-07-19",
+ "periodType": "WEEKLY",
"startDate": "2014-07-13",
},
Object {
+ "displayName": "Week 30 - 2014-07-20 - 2014-07-26",
"endDate": "2014-07-26",
"id": "2014SunW30",
"iso": "2014SunW30",
"name": "Week 30 - 2014-07-20 - 2014-07-26",
+ "periodType": "WEEKLY",
"startDate": "2014-07-20",
},
Object {
+ "displayName": "Week 31 - 2014-07-27 - 2014-08-02",
"endDate": "2014-08-02",
"id": "2014SunW31",
"iso": "2014SunW31",
"name": "Week 31 - 2014-07-27 - 2014-08-02",
+ "periodType": "WEEKLY",
"startDate": "2014-07-27",
},
Object {
+ "displayName": "Week 32 - 2014-08-03 - 2014-08-09",
"endDate": "2014-08-09",
"id": "2014SunW32",
"iso": "2014SunW32",
"name": "Week 32 - 2014-08-03 - 2014-08-09",
+ "periodType": "WEEKLY",
"startDate": "2014-08-03",
},
Object {
+ "displayName": "Week 33 - 2014-08-10 - 2014-08-16",
"endDate": "2014-08-16",
"id": "2014SunW33",
"iso": "2014SunW33",
"name": "Week 33 - 2014-08-10 - 2014-08-16",
+ "periodType": "WEEKLY",
"startDate": "2014-08-10",
},
Object {
+ "displayName": "Week 34 - 2014-08-17 - 2014-08-23",
"endDate": "2014-08-23",
"id": "2014SunW34",
"iso": "2014SunW34",
"name": "Week 34 - 2014-08-17 - 2014-08-23",
+ "periodType": "WEEKLY",
"startDate": "2014-08-17",
},
Object {
+ "displayName": "Week 35 - 2014-08-24 - 2014-08-30",
"endDate": "2014-08-30",
"id": "2014SunW35",
"iso": "2014SunW35",
"name": "Week 35 - 2014-08-24 - 2014-08-30",
+ "periodType": "WEEKLY",
"startDate": "2014-08-24",
},
Object {
+ "displayName": "Week 36 - 2014-08-31 - 2014-09-06",
"endDate": "2014-09-06",
"id": "2014SunW36",
"iso": "2014SunW36",
"name": "Week 36 - 2014-08-31 - 2014-09-06",
+ "periodType": "WEEKLY",
"startDate": "2014-08-31",
},
Object {
+ "displayName": "Week 37 - 2014-09-07 - 2014-09-13",
"endDate": "2014-09-13",
"id": "2014SunW37",
"iso": "2014SunW37",
"name": "Week 37 - 2014-09-07 - 2014-09-13",
+ "periodType": "WEEKLY",
"startDate": "2014-09-07",
},
Object {
+ "displayName": "Week 38 - 2014-09-14 - 2014-09-20",
"endDate": "2014-09-20",
"id": "2014SunW38",
"iso": "2014SunW38",
"name": "Week 38 - 2014-09-14 - 2014-09-20",
+ "periodType": "WEEKLY",
"startDate": "2014-09-14",
},
Object {
+ "displayName": "Week 39 - 2014-09-21 - 2014-09-27",
"endDate": "2014-09-27",
"id": "2014SunW39",
"iso": "2014SunW39",
"name": "Week 39 - 2014-09-21 - 2014-09-27",
+ "periodType": "WEEKLY",
"startDate": "2014-09-21",
},
Object {
+ "displayName": "Week 40 - 2014-09-28 - 2014-10-04",
"endDate": "2014-10-04",
"id": "2014SunW40",
"iso": "2014SunW40",
"name": "Week 40 - 2014-09-28 - 2014-10-04",
+ "periodType": "WEEKLY",
"startDate": "2014-09-28",
},
Object {
+ "displayName": "Week 41 - 2014-10-05 - 2014-10-11",
"endDate": "2014-10-11",
"id": "2014SunW41",
"iso": "2014SunW41",
"name": "Week 41 - 2014-10-05 - 2014-10-11",
+ "periodType": "WEEKLY",
"startDate": "2014-10-05",
},
Object {
+ "displayName": "Week 42 - 2014-10-12 - 2014-10-18",
"endDate": "2014-10-18",
"id": "2014SunW42",
"iso": "2014SunW42",
"name": "Week 42 - 2014-10-12 - 2014-10-18",
+ "periodType": "WEEKLY",
"startDate": "2014-10-12",
},
Object {
+ "displayName": "Week 43 - 2014-10-19 - 2014-10-25",
"endDate": "2014-10-25",
"id": "2014SunW43",
"iso": "2014SunW43",
"name": "Week 43 - 2014-10-19 - 2014-10-25",
+ "periodType": "WEEKLY",
"startDate": "2014-10-19",
},
Object {
+ "displayName": "Week 44 - 2014-10-26 - 2014-11-01",
"endDate": "2014-11-01",
"id": "2014SunW44",
"iso": "2014SunW44",
"name": "Week 44 - 2014-10-26 - 2014-11-01",
+ "periodType": "WEEKLY",
"startDate": "2014-10-26",
},
Object {
+ "displayName": "Week 45 - 2014-11-02 - 2014-11-08",
"endDate": "2014-11-08",
"id": "2014SunW45",
"iso": "2014SunW45",
"name": "Week 45 - 2014-11-02 - 2014-11-08",
+ "periodType": "WEEKLY",
"startDate": "2014-11-02",
},
Object {
+ "displayName": "Week 46 - 2014-11-09 - 2014-11-15",
"endDate": "2014-11-15",
"id": "2014SunW46",
"iso": "2014SunW46",
"name": "Week 46 - 2014-11-09 - 2014-11-15",
+ "periodType": "WEEKLY",
"startDate": "2014-11-09",
},
Object {
+ "displayName": "Week 47 - 2014-11-16 - 2014-11-22",
"endDate": "2014-11-22",
"id": "2014SunW47",
"iso": "2014SunW47",
"name": "Week 47 - 2014-11-16 - 2014-11-22",
+ "periodType": "WEEKLY",
"startDate": "2014-11-16",
},
Object {
+ "displayName": "Week 48 - 2014-11-23 - 2014-11-29",
"endDate": "2014-11-29",
"id": "2014SunW48",
"iso": "2014SunW48",
"name": "Week 48 - 2014-11-23 - 2014-11-29",
+ "periodType": "WEEKLY",
"startDate": "2014-11-23",
},
Object {
+ "displayName": "Week 49 - 2014-11-30 - 2014-12-06",
"endDate": "2014-12-06",
"id": "2014SunW49",
"iso": "2014SunW49",
"name": "Week 49 - 2014-11-30 - 2014-12-06",
+ "periodType": "WEEKLY",
"startDate": "2014-11-30",
},
Object {
+ "displayName": "Week 50 - 2014-12-07 - 2014-12-13",
"endDate": "2014-12-13",
"id": "2014SunW50",
"iso": "2014SunW50",
"name": "Week 50 - 2014-12-07 - 2014-12-13",
+ "periodType": "WEEKLY",
"startDate": "2014-12-07",
},
Object {
+ "displayName": "Week 51 - 2014-12-14 - 2014-12-20",
"endDate": "2014-12-20",
"id": "2014SunW51",
"iso": "2014SunW51",
"name": "Week 51 - 2014-12-14 - 2014-12-20",
+ "periodType": "WEEKLY",
"startDate": "2014-12-14",
},
Object {
+ "displayName": "Week 52 - 2014-12-21 - 2014-12-27",
"endDate": "2014-12-27",
"id": "2014SunW52",
"iso": "2014SunW52",
"name": "Week 52 - 2014-12-21 - 2014-12-27",
+ "periodType": "WEEKLY",
"startDate": "2014-12-21",
},
Object {
+ "displayName": "Week 53 - 2014-12-28 - 2015-01-03",
"endDate": "2015-01-03",
"id": "2014SunW53",
"iso": "2014SunW53",
"name": "Week 53 - 2014-12-28 - 2015-01-03",
+ "periodType": "WEEKLY",
"startDate": "2014-12-28",
},
],
@@ -4785,367 +6159,471 @@ Object {
"name": "Weekly (Start Thursday)",
"options": Array [
Object {
+ "displayName": "Week 1 - 2014-01-02 - 2014-01-08",
"endDate": "2014-01-08",
"id": "2014ThuW1",
"iso": "2014ThuW1",
"name": "Week 1 - 2014-01-02 - 2014-01-08",
+ "periodType": "WEEKLY",
"startDate": "2014-01-02",
},
Object {
+ "displayName": "Week 2 - 2014-01-09 - 2014-01-15",
"endDate": "2014-01-15",
"id": "2014ThuW2",
"iso": "2014ThuW2",
"name": "Week 2 - 2014-01-09 - 2014-01-15",
+ "periodType": "WEEKLY",
"startDate": "2014-01-09",
},
Object {
+ "displayName": "Week 3 - 2014-01-16 - 2014-01-22",
"endDate": "2014-01-22",
"id": "2014ThuW3",
"iso": "2014ThuW3",
"name": "Week 3 - 2014-01-16 - 2014-01-22",
+ "periodType": "WEEKLY",
"startDate": "2014-01-16",
},
Object {
+ "displayName": "Week 4 - 2014-01-23 - 2014-01-29",
"endDate": "2014-01-29",
"id": "2014ThuW4",
"iso": "2014ThuW4",
"name": "Week 4 - 2014-01-23 - 2014-01-29",
+ "periodType": "WEEKLY",
"startDate": "2014-01-23",
},
Object {
+ "displayName": "Week 5 - 2014-01-30 - 2014-02-05",
"endDate": "2014-02-05",
"id": "2014ThuW5",
"iso": "2014ThuW5",
"name": "Week 5 - 2014-01-30 - 2014-02-05",
+ "periodType": "WEEKLY",
"startDate": "2014-01-30",
},
Object {
+ "displayName": "Week 6 - 2014-02-06 - 2014-02-12",
"endDate": "2014-02-12",
"id": "2014ThuW6",
"iso": "2014ThuW6",
"name": "Week 6 - 2014-02-06 - 2014-02-12",
+ "periodType": "WEEKLY",
"startDate": "2014-02-06",
},
Object {
+ "displayName": "Week 7 - 2014-02-13 - 2014-02-19",
"endDate": "2014-02-19",
"id": "2014ThuW7",
"iso": "2014ThuW7",
"name": "Week 7 - 2014-02-13 - 2014-02-19",
+ "periodType": "WEEKLY",
"startDate": "2014-02-13",
},
Object {
+ "displayName": "Week 8 - 2014-02-20 - 2014-02-26",
"endDate": "2014-02-26",
"id": "2014ThuW8",
"iso": "2014ThuW8",
"name": "Week 8 - 2014-02-20 - 2014-02-26",
+ "periodType": "WEEKLY",
"startDate": "2014-02-20",
},
Object {
+ "displayName": "Week 9 - 2014-02-27 - 2014-03-05",
"endDate": "2014-03-05",
"id": "2014ThuW9",
"iso": "2014ThuW9",
"name": "Week 9 - 2014-02-27 - 2014-03-05",
+ "periodType": "WEEKLY",
"startDate": "2014-02-27",
},
Object {
+ "displayName": "Week 10 - 2014-03-06 - 2014-03-12",
"endDate": "2014-03-12",
"id": "2014ThuW10",
"iso": "2014ThuW10",
"name": "Week 10 - 2014-03-06 - 2014-03-12",
+ "periodType": "WEEKLY",
"startDate": "2014-03-06",
},
Object {
+ "displayName": "Week 11 - 2014-03-13 - 2014-03-19",
"endDate": "2014-03-19",
"id": "2014ThuW11",
"iso": "2014ThuW11",
"name": "Week 11 - 2014-03-13 - 2014-03-19",
+ "periodType": "WEEKLY",
"startDate": "2014-03-13",
},
Object {
+ "displayName": "Week 12 - 2014-03-20 - 2014-03-26",
"endDate": "2014-03-26",
"id": "2014ThuW12",
"iso": "2014ThuW12",
"name": "Week 12 - 2014-03-20 - 2014-03-26",
+ "periodType": "WEEKLY",
"startDate": "2014-03-20",
},
Object {
+ "displayName": "Week 13 - 2014-03-27 - 2014-04-02",
"endDate": "2014-04-02",
"id": "2014ThuW13",
"iso": "2014ThuW13",
"name": "Week 13 - 2014-03-27 - 2014-04-02",
+ "periodType": "WEEKLY",
"startDate": "2014-03-27",
},
Object {
+ "displayName": "Week 14 - 2014-04-03 - 2014-04-09",
"endDate": "2014-04-09",
"id": "2014ThuW14",
"iso": "2014ThuW14",
"name": "Week 14 - 2014-04-03 - 2014-04-09",
+ "periodType": "WEEKLY",
"startDate": "2014-04-03",
},
Object {
+ "displayName": "Week 15 - 2014-04-10 - 2014-04-16",
"endDate": "2014-04-16",
"id": "2014ThuW15",
"iso": "2014ThuW15",
"name": "Week 15 - 2014-04-10 - 2014-04-16",
+ "periodType": "WEEKLY",
"startDate": "2014-04-10",
},
Object {
+ "displayName": "Week 16 - 2014-04-17 - 2014-04-23",
"endDate": "2014-04-23",
"id": "2014ThuW16",
"iso": "2014ThuW16",
"name": "Week 16 - 2014-04-17 - 2014-04-23",
+ "periodType": "WEEKLY",
"startDate": "2014-04-17",
},
Object {
+ "displayName": "Week 17 - 2014-04-24 - 2014-04-30",
"endDate": "2014-04-30",
"id": "2014ThuW17",
"iso": "2014ThuW17",
"name": "Week 17 - 2014-04-24 - 2014-04-30",
+ "periodType": "WEEKLY",
"startDate": "2014-04-24",
},
Object {
+ "displayName": "Week 18 - 2014-05-01 - 2014-05-07",
"endDate": "2014-05-07",
"id": "2014ThuW18",
"iso": "2014ThuW18",
"name": "Week 18 - 2014-05-01 - 2014-05-07",
+ "periodType": "WEEKLY",
"startDate": "2014-05-01",
},
Object {
+ "displayName": "Week 19 - 2014-05-08 - 2014-05-14",
"endDate": "2014-05-14",
"id": "2014ThuW19",
"iso": "2014ThuW19",
"name": "Week 19 - 2014-05-08 - 2014-05-14",
+ "periodType": "WEEKLY",
"startDate": "2014-05-08",
},
Object {
+ "displayName": "Week 20 - 2014-05-15 - 2014-05-21",
"endDate": "2014-05-21",
"id": "2014ThuW20",
"iso": "2014ThuW20",
"name": "Week 20 - 2014-05-15 - 2014-05-21",
+ "periodType": "WEEKLY",
"startDate": "2014-05-15",
},
Object {
+ "displayName": "Week 21 - 2014-05-22 - 2014-05-28",
"endDate": "2014-05-28",
"id": "2014ThuW21",
"iso": "2014ThuW21",
"name": "Week 21 - 2014-05-22 - 2014-05-28",
+ "periodType": "WEEKLY",
"startDate": "2014-05-22",
},
Object {
+ "displayName": "Week 22 - 2014-05-29 - 2014-06-04",
"endDate": "2014-06-04",
"id": "2014ThuW22",
"iso": "2014ThuW22",
"name": "Week 22 - 2014-05-29 - 2014-06-04",
+ "periodType": "WEEKLY",
"startDate": "2014-05-29",
},
Object {
+ "displayName": "Week 23 - 2014-06-05 - 2014-06-11",
"endDate": "2014-06-11",
"id": "2014ThuW23",
"iso": "2014ThuW23",
"name": "Week 23 - 2014-06-05 - 2014-06-11",
+ "periodType": "WEEKLY",
"startDate": "2014-06-05",
},
Object {
+ "displayName": "Week 24 - 2014-06-12 - 2014-06-18",
"endDate": "2014-06-18",
"id": "2014ThuW24",
"iso": "2014ThuW24",
"name": "Week 24 - 2014-06-12 - 2014-06-18",
+ "periodType": "WEEKLY",
"startDate": "2014-06-12",
},
Object {
+ "displayName": "Week 25 - 2014-06-19 - 2014-06-25",
"endDate": "2014-06-25",
"id": "2014ThuW25",
"iso": "2014ThuW25",
"name": "Week 25 - 2014-06-19 - 2014-06-25",
+ "periodType": "WEEKLY",
"startDate": "2014-06-19",
},
Object {
+ "displayName": "Week 26 - 2014-06-26 - 2014-07-02",
"endDate": "2014-07-02",
"id": "2014ThuW26",
"iso": "2014ThuW26",
"name": "Week 26 - 2014-06-26 - 2014-07-02",
+ "periodType": "WEEKLY",
"startDate": "2014-06-26",
},
Object {
+ "displayName": "Week 27 - 2014-07-03 - 2014-07-09",
"endDate": "2014-07-09",
"id": "2014ThuW27",
"iso": "2014ThuW27",
"name": "Week 27 - 2014-07-03 - 2014-07-09",
+ "periodType": "WEEKLY",
"startDate": "2014-07-03",
},
Object {
+ "displayName": "Week 28 - 2014-07-10 - 2014-07-16",
"endDate": "2014-07-16",
"id": "2014ThuW28",
"iso": "2014ThuW28",
"name": "Week 28 - 2014-07-10 - 2014-07-16",
+ "periodType": "WEEKLY",
"startDate": "2014-07-10",
},
Object {
+ "displayName": "Week 29 - 2014-07-17 - 2014-07-23",
"endDate": "2014-07-23",
"id": "2014ThuW29",
"iso": "2014ThuW29",
"name": "Week 29 - 2014-07-17 - 2014-07-23",
+ "periodType": "WEEKLY",
"startDate": "2014-07-17",
},
Object {
+ "displayName": "Week 30 - 2014-07-24 - 2014-07-30",
"endDate": "2014-07-30",
"id": "2014ThuW30",
"iso": "2014ThuW30",
"name": "Week 30 - 2014-07-24 - 2014-07-30",
+ "periodType": "WEEKLY",
"startDate": "2014-07-24",
},
Object {
+ "displayName": "Week 31 - 2014-07-31 - 2014-08-06",
"endDate": "2014-08-06",
"id": "2014ThuW31",
"iso": "2014ThuW31",
"name": "Week 31 - 2014-07-31 - 2014-08-06",
+ "periodType": "WEEKLY",
"startDate": "2014-07-31",
},
Object {
+ "displayName": "Week 32 - 2014-08-07 - 2014-08-13",
"endDate": "2014-08-13",
"id": "2014ThuW32",
"iso": "2014ThuW32",
"name": "Week 32 - 2014-08-07 - 2014-08-13",
+ "periodType": "WEEKLY",
"startDate": "2014-08-07",
},
Object {
+ "displayName": "Week 33 - 2014-08-14 - 2014-08-20",
"endDate": "2014-08-20",
"id": "2014ThuW33",
"iso": "2014ThuW33",
"name": "Week 33 - 2014-08-14 - 2014-08-20",
+ "periodType": "WEEKLY",
"startDate": "2014-08-14",
},
Object {
+ "displayName": "Week 34 - 2014-08-21 - 2014-08-27",
"endDate": "2014-08-27",
"id": "2014ThuW34",
"iso": "2014ThuW34",
"name": "Week 34 - 2014-08-21 - 2014-08-27",
+ "periodType": "WEEKLY",
"startDate": "2014-08-21",
},
Object {
+ "displayName": "Week 35 - 2014-08-28 - 2014-09-03",
"endDate": "2014-09-03",
"id": "2014ThuW35",
"iso": "2014ThuW35",
"name": "Week 35 - 2014-08-28 - 2014-09-03",
+ "periodType": "WEEKLY",
"startDate": "2014-08-28",
},
Object {
+ "displayName": "Week 36 - 2014-09-04 - 2014-09-10",
"endDate": "2014-09-10",
"id": "2014ThuW36",
"iso": "2014ThuW36",
"name": "Week 36 - 2014-09-04 - 2014-09-10",
+ "periodType": "WEEKLY",
"startDate": "2014-09-04",
},
Object {
+ "displayName": "Week 37 - 2014-09-11 - 2014-09-17",
"endDate": "2014-09-17",
"id": "2014ThuW37",
"iso": "2014ThuW37",
"name": "Week 37 - 2014-09-11 - 2014-09-17",
+ "periodType": "WEEKLY",
"startDate": "2014-09-11",
},
Object {
+ "displayName": "Week 38 - 2014-09-18 - 2014-09-24",
"endDate": "2014-09-24",
"id": "2014ThuW38",
"iso": "2014ThuW38",
"name": "Week 38 - 2014-09-18 - 2014-09-24",
+ "periodType": "WEEKLY",
"startDate": "2014-09-18",
},
Object {
+ "displayName": "Week 39 - 2014-09-25 - 2014-10-01",
"endDate": "2014-10-01",
"id": "2014ThuW39",
"iso": "2014ThuW39",
"name": "Week 39 - 2014-09-25 - 2014-10-01",
+ "periodType": "WEEKLY",
"startDate": "2014-09-25",
},
Object {
+ "displayName": "Week 40 - 2014-10-02 - 2014-10-08",
"endDate": "2014-10-08",
"id": "2014ThuW40",
"iso": "2014ThuW40",
"name": "Week 40 - 2014-10-02 - 2014-10-08",
+ "periodType": "WEEKLY",
"startDate": "2014-10-02",
},
Object {
+ "displayName": "Week 41 - 2014-10-09 - 2014-10-15",
"endDate": "2014-10-15",
"id": "2014ThuW41",
"iso": "2014ThuW41",
"name": "Week 41 - 2014-10-09 - 2014-10-15",
+ "periodType": "WEEKLY",
"startDate": "2014-10-09",
},
Object {
+ "displayName": "Week 42 - 2014-10-16 - 2014-10-22",
"endDate": "2014-10-22",
"id": "2014ThuW42",
"iso": "2014ThuW42",
"name": "Week 42 - 2014-10-16 - 2014-10-22",
+ "periodType": "WEEKLY",
"startDate": "2014-10-16",
},
Object {
+ "displayName": "Week 43 - 2014-10-23 - 2014-10-29",
"endDate": "2014-10-29",
"id": "2014ThuW43",
"iso": "2014ThuW43",
"name": "Week 43 - 2014-10-23 - 2014-10-29",
+ "periodType": "WEEKLY",
"startDate": "2014-10-23",
},
Object {
+ "displayName": "Week 44 - 2014-10-30 - 2014-11-05",
"endDate": "2014-11-05",
"id": "2014ThuW44",
"iso": "2014ThuW44",
"name": "Week 44 - 2014-10-30 - 2014-11-05",
+ "periodType": "WEEKLY",
"startDate": "2014-10-30",
},
Object {
+ "displayName": "Week 45 - 2014-11-06 - 2014-11-12",
"endDate": "2014-11-12",
"id": "2014ThuW45",
"iso": "2014ThuW45",
"name": "Week 45 - 2014-11-06 - 2014-11-12",
+ "periodType": "WEEKLY",
"startDate": "2014-11-06",
},
Object {
+ "displayName": "Week 46 - 2014-11-13 - 2014-11-19",
"endDate": "2014-11-19",
"id": "2014ThuW46",
"iso": "2014ThuW46",
"name": "Week 46 - 2014-11-13 - 2014-11-19",
+ "periodType": "WEEKLY",
"startDate": "2014-11-13",
},
Object {
+ "displayName": "Week 47 - 2014-11-20 - 2014-11-26",
"endDate": "2014-11-26",
"id": "2014ThuW47",
"iso": "2014ThuW47",
"name": "Week 47 - 2014-11-20 - 2014-11-26",
+ "periodType": "WEEKLY",
"startDate": "2014-11-20",
},
Object {
+ "displayName": "Week 48 - 2014-11-27 - 2014-12-03",
"endDate": "2014-12-03",
"id": "2014ThuW48",
"iso": "2014ThuW48",
"name": "Week 48 - 2014-11-27 - 2014-12-03",
+ "periodType": "WEEKLY",
"startDate": "2014-11-27",
},
Object {
+ "displayName": "Week 49 - 2014-12-04 - 2014-12-10",
"endDate": "2014-12-10",
"id": "2014ThuW49",
"iso": "2014ThuW49",
"name": "Week 49 - 2014-12-04 - 2014-12-10",
+ "periodType": "WEEKLY",
"startDate": "2014-12-04",
},
Object {
+ "displayName": "Week 50 - 2014-12-11 - 2014-12-17",
"endDate": "2014-12-17",
"id": "2014ThuW50",
"iso": "2014ThuW50",
"name": "Week 50 - 2014-12-11 - 2014-12-17",
+ "periodType": "WEEKLY",
"startDate": "2014-12-11",
},
Object {
+ "displayName": "Week 51 - 2014-12-18 - 2014-12-24",
"endDate": "2014-12-24",
"id": "2014ThuW51",
"iso": "2014ThuW51",
"name": "Week 51 - 2014-12-18 - 2014-12-24",
+ "periodType": "WEEKLY",
"startDate": "2014-12-18",
},
Object {
+ "displayName": "Week 52 - 2014-12-25 - 2014-12-31",
"endDate": "2014-12-31",
"id": "2014ThuW52",
"iso": "2014ThuW52",
"name": "Week 52 - 2014-12-25 - 2014-12-31",
+ "periodType": "WEEKLY",
"startDate": "2014-12-25",
},
],
@@ -5159,367 +6637,471 @@ Object {
"name": "Weekly (Start Wednesday)",
"options": Array [
Object {
+ "displayName": "Week 1 - 2014-01-01 - 2014-01-07",
"endDate": "2014-01-07",
"id": "2014WedW1",
"iso": "2014WedW1",
"name": "Week 1 - 2014-01-01 - 2014-01-07",
+ "periodType": "WEEKLY",
"startDate": "2014-01-01",
},
Object {
+ "displayName": "Week 2 - 2014-01-08 - 2014-01-14",
"endDate": "2014-01-14",
"id": "2014WedW2",
"iso": "2014WedW2",
"name": "Week 2 - 2014-01-08 - 2014-01-14",
+ "periodType": "WEEKLY",
"startDate": "2014-01-08",
},
Object {
+ "displayName": "Week 3 - 2014-01-15 - 2014-01-21",
"endDate": "2014-01-21",
"id": "2014WedW3",
"iso": "2014WedW3",
"name": "Week 3 - 2014-01-15 - 2014-01-21",
+ "periodType": "WEEKLY",
"startDate": "2014-01-15",
},
Object {
+ "displayName": "Week 4 - 2014-01-22 - 2014-01-28",
"endDate": "2014-01-28",
"id": "2014WedW4",
"iso": "2014WedW4",
"name": "Week 4 - 2014-01-22 - 2014-01-28",
+ "periodType": "WEEKLY",
"startDate": "2014-01-22",
},
Object {
+ "displayName": "Week 5 - 2014-01-29 - 2014-02-04",
"endDate": "2014-02-04",
"id": "2014WedW5",
"iso": "2014WedW5",
"name": "Week 5 - 2014-01-29 - 2014-02-04",
+ "periodType": "WEEKLY",
"startDate": "2014-01-29",
},
Object {
+ "displayName": "Week 6 - 2014-02-05 - 2014-02-11",
"endDate": "2014-02-11",
"id": "2014WedW6",
"iso": "2014WedW6",
"name": "Week 6 - 2014-02-05 - 2014-02-11",
+ "periodType": "WEEKLY",
"startDate": "2014-02-05",
},
Object {
+ "displayName": "Week 7 - 2014-02-12 - 2014-02-18",
"endDate": "2014-02-18",
"id": "2014WedW7",
"iso": "2014WedW7",
"name": "Week 7 - 2014-02-12 - 2014-02-18",
+ "periodType": "WEEKLY",
"startDate": "2014-02-12",
},
Object {
+ "displayName": "Week 8 - 2014-02-19 - 2014-02-25",
"endDate": "2014-02-25",
"id": "2014WedW8",
"iso": "2014WedW8",
"name": "Week 8 - 2014-02-19 - 2014-02-25",
+ "periodType": "WEEKLY",
"startDate": "2014-02-19",
},
Object {
+ "displayName": "Week 9 - 2014-02-26 - 2014-03-04",
"endDate": "2014-03-04",
"id": "2014WedW9",
"iso": "2014WedW9",
"name": "Week 9 - 2014-02-26 - 2014-03-04",
+ "periodType": "WEEKLY",
"startDate": "2014-02-26",
},
Object {
+ "displayName": "Week 10 - 2014-03-05 - 2014-03-11",
"endDate": "2014-03-11",
"id": "2014WedW10",
"iso": "2014WedW10",
"name": "Week 10 - 2014-03-05 - 2014-03-11",
+ "periodType": "WEEKLY",
"startDate": "2014-03-05",
},
Object {
+ "displayName": "Week 11 - 2014-03-12 - 2014-03-18",
"endDate": "2014-03-18",
"id": "2014WedW11",
"iso": "2014WedW11",
"name": "Week 11 - 2014-03-12 - 2014-03-18",
+ "periodType": "WEEKLY",
"startDate": "2014-03-12",
},
Object {
+ "displayName": "Week 12 - 2014-03-19 - 2014-03-25",
"endDate": "2014-03-25",
"id": "2014WedW12",
"iso": "2014WedW12",
"name": "Week 12 - 2014-03-19 - 2014-03-25",
+ "periodType": "WEEKLY",
"startDate": "2014-03-19",
},
Object {
+ "displayName": "Week 13 - 2014-03-26 - 2014-04-01",
"endDate": "2014-04-01",
"id": "2014WedW13",
"iso": "2014WedW13",
"name": "Week 13 - 2014-03-26 - 2014-04-01",
+ "periodType": "WEEKLY",
"startDate": "2014-03-26",
},
Object {
+ "displayName": "Week 14 - 2014-04-02 - 2014-04-08",
"endDate": "2014-04-08",
"id": "2014WedW14",
"iso": "2014WedW14",
"name": "Week 14 - 2014-04-02 - 2014-04-08",
+ "periodType": "WEEKLY",
"startDate": "2014-04-02",
},
Object {
+ "displayName": "Week 15 - 2014-04-09 - 2014-04-15",
"endDate": "2014-04-15",
"id": "2014WedW15",
"iso": "2014WedW15",
"name": "Week 15 - 2014-04-09 - 2014-04-15",
+ "periodType": "WEEKLY",
"startDate": "2014-04-09",
},
Object {
+ "displayName": "Week 16 - 2014-04-16 - 2014-04-22",
"endDate": "2014-04-22",
"id": "2014WedW16",
"iso": "2014WedW16",
"name": "Week 16 - 2014-04-16 - 2014-04-22",
+ "periodType": "WEEKLY",
"startDate": "2014-04-16",
},
Object {
+ "displayName": "Week 17 - 2014-04-23 - 2014-04-29",
"endDate": "2014-04-29",
"id": "2014WedW17",
"iso": "2014WedW17",
"name": "Week 17 - 2014-04-23 - 2014-04-29",
+ "periodType": "WEEKLY",
"startDate": "2014-04-23",
},
Object {
+ "displayName": "Week 18 - 2014-04-30 - 2014-05-06",
"endDate": "2014-05-06",
"id": "2014WedW18",
"iso": "2014WedW18",
"name": "Week 18 - 2014-04-30 - 2014-05-06",
+ "periodType": "WEEKLY",
"startDate": "2014-04-30",
},
Object {
+ "displayName": "Week 19 - 2014-05-07 - 2014-05-13",
"endDate": "2014-05-13",
"id": "2014WedW19",
"iso": "2014WedW19",
"name": "Week 19 - 2014-05-07 - 2014-05-13",
+ "periodType": "WEEKLY",
"startDate": "2014-05-07",
},
Object {
+ "displayName": "Week 20 - 2014-05-14 - 2014-05-20",
"endDate": "2014-05-20",
"id": "2014WedW20",
"iso": "2014WedW20",
"name": "Week 20 - 2014-05-14 - 2014-05-20",
+ "periodType": "WEEKLY",
"startDate": "2014-05-14",
},
Object {
+ "displayName": "Week 21 - 2014-05-21 - 2014-05-27",
"endDate": "2014-05-27",
"id": "2014WedW21",
"iso": "2014WedW21",
"name": "Week 21 - 2014-05-21 - 2014-05-27",
+ "periodType": "WEEKLY",
"startDate": "2014-05-21",
},
Object {
+ "displayName": "Week 22 - 2014-05-28 - 2014-06-03",
"endDate": "2014-06-03",
"id": "2014WedW22",
"iso": "2014WedW22",
"name": "Week 22 - 2014-05-28 - 2014-06-03",
+ "periodType": "WEEKLY",
"startDate": "2014-05-28",
},
Object {
+ "displayName": "Week 23 - 2014-06-04 - 2014-06-10",
"endDate": "2014-06-10",
"id": "2014WedW23",
"iso": "2014WedW23",
"name": "Week 23 - 2014-06-04 - 2014-06-10",
+ "periodType": "WEEKLY",
"startDate": "2014-06-04",
},
Object {
+ "displayName": "Week 24 - 2014-06-11 - 2014-06-17",
"endDate": "2014-06-17",
"id": "2014WedW24",
"iso": "2014WedW24",
"name": "Week 24 - 2014-06-11 - 2014-06-17",
+ "periodType": "WEEKLY",
"startDate": "2014-06-11",
},
Object {
+ "displayName": "Week 25 - 2014-06-18 - 2014-06-24",
"endDate": "2014-06-24",
"id": "2014WedW25",
"iso": "2014WedW25",
"name": "Week 25 - 2014-06-18 - 2014-06-24",
+ "periodType": "WEEKLY",
"startDate": "2014-06-18",
},
Object {
+ "displayName": "Week 26 - 2014-06-25 - 2014-07-01",
"endDate": "2014-07-01",
"id": "2014WedW26",
"iso": "2014WedW26",
"name": "Week 26 - 2014-06-25 - 2014-07-01",
+ "periodType": "WEEKLY",
"startDate": "2014-06-25",
},
Object {
+ "displayName": "Week 27 - 2014-07-02 - 2014-07-08",
"endDate": "2014-07-08",
"id": "2014WedW27",
"iso": "2014WedW27",
"name": "Week 27 - 2014-07-02 - 2014-07-08",
+ "periodType": "WEEKLY",
"startDate": "2014-07-02",
},
Object {
+ "displayName": "Week 28 - 2014-07-09 - 2014-07-15",
"endDate": "2014-07-15",
"id": "2014WedW28",
"iso": "2014WedW28",
"name": "Week 28 - 2014-07-09 - 2014-07-15",
+ "periodType": "WEEKLY",
"startDate": "2014-07-09",
},
Object {
+ "displayName": "Week 29 - 2014-07-16 - 2014-07-22",
"endDate": "2014-07-22",
"id": "2014WedW29",
"iso": "2014WedW29",
"name": "Week 29 - 2014-07-16 - 2014-07-22",
+ "periodType": "WEEKLY",
"startDate": "2014-07-16",
},
Object {
+ "displayName": "Week 30 - 2014-07-23 - 2014-07-29",
"endDate": "2014-07-29",
"id": "2014WedW30",
"iso": "2014WedW30",
"name": "Week 30 - 2014-07-23 - 2014-07-29",
+ "periodType": "WEEKLY",
"startDate": "2014-07-23",
},
Object {
+ "displayName": "Week 31 - 2014-07-30 - 2014-08-05",
"endDate": "2014-08-05",
"id": "2014WedW31",
"iso": "2014WedW31",
"name": "Week 31 - 2014-07-30 - 2014-08-05",
+ "periodType": "WEEKLY",
"startDate": "2014-07-30",
},
Object {
+ "displayName": "Week 32 - 2014-08-06 - 2014-08-12",
"endDate": "2014-08-12",
"id": "2014WedW32",
"iso": "2014WedW32",
"name": "Week 32 - 2014-08-06 - 2014-08-12",
+ "periodType": "WEEKLY",
"startDate": "2014-08-06",
},
Object {
+ "displayName": "Week 33 - 2014-08-13 - 2014-08-19",
"endDate": "2014-08-19",
"id": "2014WedW33",
"iso": "2014WedW33",
"name": "Week 33 - 2014-08-13 - 2014-08-19",
+ "periodType": "WEEKLY",
"startDate": "2014-08-13",
},
Object {
+ "displayName": "Week 34 - 2014-08-20 - 2014-08-26",
"endDate": "2014-08-26",
"id": "2014WedW34",
"iso": "2014WedW34",
"name": "Week 34 - 2014-08-20 - 2014-08-26",
+ "periodType": "WEEKLY",
"startDate": "2014-08-20",
},
Object {
+ "displayName": "Week 35 - 2014-08-27 - 2014-09-02",
"endDate": "2014-09-02",
"id": "2014WedW35",
"iso": "2014WedW35",
"name": "Week 35 - 2014-08-27 - 2014-09-02",
+ "periodType": "WEEKLY",
"startDate": "2014-08-27",
},
Object {
+ "displayName": "Week 36 - 2014-09-03 - 2014-09-09",
"endDate": "2014-09-09",
"id": "2014WedW36",
"iso": "2014WedW36",
"name": "Week 36 - 2014-09-03 - 2014-09-09",
+ "periodType": "WEEKLY",
"startDate": "2014-09-03",
},
Object {
+ "displayName": "Week 37 - 2014-09-10 - 2014-09-16",
"endDate": "2014-09-16",
"id": "2014WedW37",
"iso": "2014WedW37",
"name": "Week 37 - 2014-09-10 - 2014-09-16",
+ "periodType": "WEEKLY",
"startDate": "2014-09-10",
},
Object {
+ "displayName": "Week 38 - 2014-09-17 - 2014-09-23",
"endDate": "2014-09-23",
"id": "2014WedW38",
"iso": "2014WedW38",
"name": "Week 38 - 2014-09-17 - 2014-09-23",
+ "periodType": "WEEKLY",
"startDate": "2014-09-17",
},
Object {
+ "displayName": "Week 39 - 2014-09-24 - 2014-09-30",
"endDate": "2014-09-30",
"id": "2014WedW39",
"iso": "2014WedW39",
"name": "Week 39 - 2014-09-24 - 2014-09-30",
+ "periodType": "WEEKLY",
"startDate": "2014-09-24",
},
Object {
+ "displayName": "Week 40 - 2014-10-01 - 2014-10-07",
"endDate": "2014-10-07",
"id": "2014WedW40",
"iso": "2014WedW40",
"name": "Week 40 - 2014-10-01 - 2014-10-07",
+ "periodType": "WEEKLY",
"startDate": "2014-10-01",
},
Object {
+ "displayName": "Week 41 - 2014-10-08 - 2014-10-14",
"endDate": "2014-10-14",
"id": "2014WedW41",
"iso": "2014WedW41",
"name": "Week 41 - 2014-10-08 - 2014-10-14",
+ "periodType": "WEEKLY",
"startDate": "2014-10-08",
},
Object {
+ "displayName": "Week 42 - 2014-10-15 - 2014-10-21",
"endDate": "2014-10-21",
"id": "2014WedW42",
"iso": "2014WedW42",
"name": "Week 42 - 2014-10-15 - 2014-10-21",
+ "periodType": "WEEKLY",
"startDate": "2014-10-15",
},
Object {
+ "displayName": "Week 43 - 2014-10-22 - 2014-10-28",
"endDate": "2014-10-28",
"id": "2014WedW43",
"iso": "2014WedW43",
"name": "Week 43 - 2014-10-22 - 2014-10-28",
+ "periodType": "WEEKLY",
"startDate": "2014-10-22",
},
Object {
+ "displayName": "Week 44 - 2014-10-29 - 2014-11-04",
"endDate": "2014-11-04",
"id": "2014WedW44",
"iso": "2014WedW44",
"name": "Week 44 - 2014-10-29 - 2014-11-04",
+ "periodType": "WEEKLY",
"startDate": "2014-10-29",
},
Object {
+ "displayName": "Week 45 - 2014-11-05 - 2014-11-11",
"endDate": "2014-11-11",
"id": "2014WedW45",
"iso": "2014WedW45",
"name": "Week 45 - 2014-11-05 - 2014-11-11",
+ "periodType": "WEEKLY",
"startDate": "2014-11-05",
},
Object {
+ "displayName": "Week 46 - 2014-11-12 - 2014-11-18",
"endDate": "2014-11-18",
"id": "2014WedW46",
"iso": "2014WedW46",
"name": "Week 46 - 2014-11-12 - 2014-11-18",
+ "periodType": "WEEKLY",
"startDate": "2014-11-12",
},
Object {
+ "displayName": "Week 47 - 2014-11-19 - 2014-11-25",
"endDate": "2014-11-25",
"id": "2014WedW47",
"iso": "2014WedW47",
"name": "Week 47 - 2014-11-19 - 2014-11-25",
+ "periodType": "WEEKLY",
"startDate": "2014-11-19",
},
Object {
+ "displayName": "Week 48 - 2014-11-26 - 2014-12-02",
"endDate": "2014-12-02",
"id": "2014WedW48",
"iso": "2014WedW48",
"name": "Week 48 - 2014-11-26 - 2014-12-02",
+ "periodType": "WEEKLY",
"startDate": "2014-11-26",
},
Object {
+ "displayName": "Week 49 - 2014-12-03 - 2014-12-09",
"endDate": "2014-12-09",
"id": "2014WedW49",
"iso": "2014WedW49",
"name": "Week 49 - 2014-12-03 - 2014-12-09",
+ "periodType": "WEEKLY",
"startDate": "2014-12-03",
},
Object {
+ "displayName": "Week 50 - 2014-12-10 - 2014-12-16",
"endDate": "2014-12-16",
"id": "2014WedW50",
"iso": "2014WedW50",
"name": "Week 50 - 2014-12-10 - 2014-12-16",
+ "periodType": "WEEKLY",
"startDate": "2014-12-10",
},
Object {
+ "displayName": "Week 51 - 2014-12-17 - 2014-12-23",
"endDate": "2014-12-23",
"id": "2014WedW51",
"iso": "2014WedW51",
"name": "Week 51 - 2014-12-17 - 2014-12-23",
+ "periodType": "WEEKLY",
"startDate": "2014-12-17",
},
Object {
+ "displayName": "Week 52 - 2014-12-24 - 2014-12-30",
"endDate": "2014-12-30",
"id": "2014WedW52",
"iso": "2014WedW52",
"name": "Week 52 - 2014-12-24 - 2014-12-30",
+ "periodType": "WEEKLY",
"startDate": "2014-12-24",
},
],
@@ -5533,73 +7115,93 @@ Object {
"name": "Yearly",
"options": Array [
Object {
+ "displayName": "2005",
"endDate": "2005-12-31",
"id": "2005",
"iso": "2005",
"name": "2005",
+ "periodType": "YEARLY",
"startDate": "2005-01-01",
},
Object {
+ "displayName": "2006",
"endDate": "2006-12-31",
"id": "2006",
"iso": "2006",
"name": "2006",
+ "periodType": "YEARLY",
"startDate": "2006-01-01",
},
Object {
+ "displayName": "2007",
"endDate": "2007-12-31",
"id": "2007",
"iso": "2007",
"name": "2007",
+ "periodType": "YEARLY",
"startDate": "2007-01-01",
},
Object {
+ "displayName": "2008",
"endDate": "2008-12-31",
"id": "2008",
"iso": "2008",
"name": "2008",
+ "periodType": "YEARLY",
"startDate": "2008-01-01",
},
Object {
+ "displayName": "2009",
"endDate": "2009-12-31",
"id": "2009",
"iso": "2009",
"name": "2009",
+ "periodType": "YEARLY",
"startDate": "2009-01-01",
},
Object {
+ "displayName": "2010",
"endDate": "2010-12-31",
"id": "2010",
"iso": "2010",
"name": "2010",
+ "periodType": "YEARLY",
"startDate": "2010-01-01",
},
Object {
+ "displayName": "2011",
"endDate": "2011-12-31",
"id": "2011",
"iso": "2011",
"name": "2011",
+ "periodType": "YEARLY",
"startDate": "2011-01-01",
},
Object {
+ "displayName": "2012",
"endDate": "2012-12-31",
"id": "2012",
"iso": "2012",
"name": "2012",
+ "periodType": "YEARLY",
"startDate": "2012-01-01",
},
Object {
+ "displayName": "2013",
"endDate": "2013-12-31",
"id": "2013",
"iso": "2013",
"name": "2013",
+ "periodType": "YEARLY",
"startDate": "2013-01-01",
},
Object {
+ "displayName": "2014",
"endDate": "2014-12-31",
"id": "2014",
"iso": "2014",
"name": "2014",
+ "periodType": "YEARLY",
"startDate": "2014-01-01",
},
],
diff --git a/yarn.lock b/yarn.lock
index 814fd22bd..1cc77afd3 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -2445,28 +2445,31 @@
semver "^7.3.5"
yargs "^16.2.0"
-"@dhis2/d2-i18n@^1.1.0":
- version "1.1.0"
- resolved "https://registry.yarnpkg.com/@dhis2/d2-i18n/-/d2-i18n-1.1.0.tgz#ec777c5091f747e4c5aa4f9801c62ba4d1ef3d16"
- integrity sha512-x3u58goDQsMfBzy50koxNrJjofJTtjRZOfz6f6Py/wMMJfp/T6vZjWMQgcfWH0JrV6d04K1RTt6bI05wqsVQvg==
+"@dhis2/d2-i18n@^1.1.0", "@dhis2/d2-i18n@^1.1.3":
+ version "1.1.3"
+ resolved "https://registry.yarnpkg.com/@dhis2/d2-i18n/-/d2-i18n-1.1.3.tgz#ad73030f7cfceeed1b5bcaad86a9b336130bdfb1"
+ integrity sha512-vOu6RDNumOJM396mHt35bETk9ai9b6XJyAwlUy1HstUZNvfET61F8rjCmMuXZU6zJ8ELux8kMFqlH8IG0vDJmA==
dependencies:
+ "@types/i18next" "^11.9.0"
i18next "^10.3"
moment "^2.24.0"
-"@dhis2/multi-calendar-dates@1.0.0":
- version "1.0.0"
- resolved "https://registry.yarnpkg.com/@dhis2/multi-calendar-dates/-/multi-calendar-dates-1.0.0.tgz#bf7f49aecdffa9781837a5d60d56a094b74ab4df"
- integrity sha512-IB9a+feuS6yE4lpZj/eZ9uBmpYI7Hxitl2Op0JjoRL4tP+p6uw4ns9cjoSdUeIU9sOAxVZV7oQqSyIw+9P6YjQ==
+"@dhis2/multi-calendar-dates@^1.1.1":
+ version "1.2.1"
+ resolved "https://registry.yarnpkg.com/@dhis2/multi-calendar-dates/-/multi-calendar-dates-1.2.1.tgz#d31ac037302879ae624d72d2373ac455b7e357e8"
+ integrity sha512-lIYwpDbHXKnquvkMDuT2E+V/MwjPDIPIfLi9xfWq5SkuZE3zSl0g65echWYySeZ7EzgRhrtYwA3nuWwuGfcV5Q==
dependencies:
- "@js-temporal/polyfill" "^0.4.2"
+ "@dhis2/d2-i18n" "^1.1.3"
+ "@js-temporal/polyfill" "0.4.3"
classnames "^2.3.2"
-"@dhis2/multi-calendar-dates@^1.1.1":
- version "1.1.1"
- resolved "https://registry.yarnpkg.com/@dhis2/multi-calendar-dates/-/multi-calendar-dates-1.1.1.tgz#fb76a77114ce0b757db7dd9f588d1a47809732da"
- integrity sha512-kaisVuRGfdqY/Up6sWqgc81K67ymPVoRYgYRcT29z61ol2WhiTXTSTuRX/gDO1VKjmskeB5/badRrdLMf4BBUA==
+"@dhis2/multi-calendar-dates@^1.2.2":
+ version "1.2.2"
+ resolved "https://registry.yarnpkg.com/@dhis2/multi-calendar-dates/-/multi-calendar-dates-1.2.2.tgz#c34e5172474ddc73ad829515ed4c489fb8023669"
+ integrity sha512-Bl4y2+oDMJLZwtQ1Djfd+wJxOkGixBl6SCuLNH08B3RJSTwF/HcwgtY0vv7tcKUs63SwS7fK6ittXphyB4HJjQ==
dependencies:
- "@js-temporal/polyfill" "^0.4.2"
+ "@dhis2/d2-i18n" "^1.1.3"
+ "@js-temporal/polyfill" "0.4.3"
classnames "^2.3.2"
"@dhis2/prop-types@^3.1.2":
@@ -3280,7 +3283,7 @@
"@jridgewell/resolve-uri" "3.1.0"
"@jridgewell/sourcemap-codec" "1.4.14"
-"@js-temporal/polyfill@^0.4.2":
+"@js-temporal/polyfill@0.4.3":
version "0.4.3"
resolved "https://registry.yarnpkg.com/@js-temporal/polyfill/-/polyfill-0.4.3.tgz#e8f8cf86745eb5050679c46a5ebedb9a9cc1f09b"
integrity sha512-6Fmjo/HlkyVCmJzAPnvtEWlcbQUSRhi8qlN9EtJA/wP7FqXsevLLrlojR44kzNzrRkpf7eDJ+z7b4xQD/Ycypw==
@@ -4959,6 +4962,11 @@
resolved "https://registry.yarnpkg.com/@types/html-minifier-terser/-/html-minifier-terser-5.1.2.tgz#693b316ad323ea97eed6b38ed1a3cc02b1672b57"
integrity sha512-h4lTMgMJctJybDp8CQrxTUiiYmedihHWkjnF/8Pxseu2S6Nlfcy8kwboQ8yejh456rP2yWoEVm1sS/FVsfM48w==
+"@types/i18next@^11.9.0":
+ version "11.9.3"
+ resolved "https://registry.yarnpkg.com/@types/i18next/-/i18next-11.9.3.tgz#04d84c6539908ad69665d26d8967f942d1638550"
+ integrity sha512-snM7bMKy6gt7UYdpjsxycqSCAy0fr2JVPY0B8tJ2vp9bN58cE7C880k20PWFM4KXxQ3KsstKM8DLCawGCIH0tg==
+
"@types/is-function@^1.0.0":
version "1.0.1"
resolved "https://registry.yarnpkg.com/@types/is-function/-/is-function-1.0.1.tgz#2d024eace950c836d9e3335a66b97960ae41d022"
From e1ef741792be708319a5e3d1a14eaa9867e1c9e8 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Tue, 25 Jun 2024 09:29:54 +0000
Subject: [PATCH 093/130] chore(release): cut 26.7.5 [skip ci]
## [26.7.5](https://github.com/dhis2/analytics/compare/v26.7.4...v26.7.5) (2024-06-25)
### Bug Fixes
* update multicalendar dep for translations (DHIS2-16904) ([#1685](https://github.com/dhis2/analytics/issues/1685)) ([b3a48ba](https://github.com/dhis2/analytics/commit/b3a48ba8cff9956468a2670c0dda16549247bd18))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index d4a911d2c..a70157b76 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.7.5](https://github.com/dhis2/analytics/compare/v26.7.4...v26.7.5) (2024-06-25)
+
+
+### Bug Fixes
+
+* update multicalendar dep for translations (DHIS2-16904) ([#1685](https://github.com/dhis2/analytics/issues/1685)) ([b3a48ba](https://github.com/dhis2/analytics/commit/b3a48ba8cff9956468a2670c0dda16549247bd18))
+
## [26.7.4](https://github.com/dhis2/analytics/compare/v26.7.3...v26.7.4) (2024-06-20)
diff --git a/package.json b/package.json
index 06180396b..a437b7fda 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.4",
+ "version": "26.7.5",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From e93b106f7e0b3ab9ebae8a21a07d5cebee3d48d3 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jan=20Henrik=20=C3=98verland?=
Date: Wed, 26 Jun 2024 16:26:18 +0200
Subject: [PATCH 094/130] fix: apply legend to all numeric and boolean types
(DHIS2-17611) (#1683)
* fix: apply to all numeric and boolean types
* chore: remove obsolete comment, remove test file
* chore: add back i18n, weird issue
---
i18n/en.pot | 4 ++--
src/components/PivotTable/PivotTableValueCell.js | 9 ++++++---
src/modules/renderValue.js | 7 +++++--
src/modules/valueTypes.js | 3 +++
4 files changed, 16 insertions(+), 7 deletions(-)
diff --git a/i18n/en.pot b/i18n/en.pot
index 936f74c49..7aea739a6 100644
--- a/i18n/en.pot
+++ b/i18n/en.pot
@@ -5,8 +5,8 @@ msgstr ""
"Content-Type: text/plain; charset=utf-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=(n != 1)\n"
-"POT-Creation-Date: 2024-01-25T12:05:03.360Z\n"
-"PO-Revision-Date: 2024-01-25T12:05:03.360Z\n"
+"POT-Creation-Date: 2024-06-26T14:09:30.876Z\n"
+"PO-Revision-Date: 2024-06-26T14:09:30.876Z\n"
msgid "view only"
msgstr "view only"
diff --git a/src/components/PivotTable/PivotTableValueCell.js b/src/components/PivotTable/PivotTableValueCell.js
index 9013a0a83..78d204f2c 100644
--- a/src/components/PivotTable/PivotTableValueCell.js
+++ b/src/components/PivotTable/PivotTableValueCell.js
@@ -2,7 +2,10 @@ import PropTypes from 'prop-types'
import React, { useRef } from 'react'
import { applyLegendSet } from '../../modules/pivotTable/applyLegendSet.js'
import { CELL_TYPE_VALUE } from '../../modules/pivotTable/pivotTableConstants.js'
-import { VALUE_TYPE_NUMBER } from '../../modules/valueTypes.js'
+import {
+ isNumericValueType,
+ isBooleanValueType,
+} from '../../modules/valueTypes.js'
import { PivotTableCell } from './PivotTableCell.js'
import { PivotTableEmptyCell } from './PivotTableEmptyCell.js'
import { usePivotTableEngine } from './PivotTableEngineContext.js'
@@ -43,10 +46,10 @@ export const PivotTableValueCell = ({
)
}
- // TODO: Add support for 'INTEGER' type (requires server changes)
const legendStyle =
cellContent.cellType === CELL_TYPE_VALUE &&
- cellContent.valueType === VALUE_TYPE_NUMBER
+ (isNumericValueType(cellContent.valueType) ||
+ isBooleanValueType(cellContent.valueType))
? applyLegendSet(
cellContent.rawValue,
cellContent.dxDimension,
diff --git a/src/modules/renderValue.js b/src/modules/renderValue.js
index a65d8a6d8..5e87629f1 100644
--- a/src/modules/renderValue.js
+++ b/src/modules/renderValue.js
@@ -2,7 +2,7 @@ import {
NUMBER_TYPE_ROW_PERCENTAGE,
NUMBER_TYPE_COLUMN_PERCENTAGE,
} from './pivotTable/pivotTableConstants.js'
-import { isNumericValueType } from './valueTypes.js'
+import { isNumericValueType, isBooleanValueType } from './valueTypes.js'
const trimTrailingZeros = (stringValue) => stringValue.replace(/\.?0+$/, '')
@@ -53,7 +53,10 @@ const toFixedPrecisionString = (value, skipRounding) => {
}
export const renderValue = (value, valueType, visualization) => {
- if (!isNumericValueType(valueType) || value === undefined) {
+ if (
+ !(isNumericValueType(valueType) || isBooleanValueType(valueType)) ||
+ value === undefined
+ ) {
return String(value).replace(/[^\S\n]+/, ' ')
}
diff --git a/src/modules/valueTypes.js b/src/modules/valueTypes.js
index cf5dc01f0..89462b5c6 100644
--- a/src/modules/valueTypes.js
+++ b/src/modules/valueTypes.js
@@ -34,4 +34,7 @@ const NUMERIC_VALUE_TYPES = [
VALUE_TYPE_INTEGER_ZERO_OR_POSITIVE,
]
+const BOOLEAN_VALUE_TYPES = [VALUE_TYPE_BOOLEAN, VALUE_TYPE_TRUE_ONLY]
+
export const isNumericValueType = (type) => NUMERIC_VALUE_TYPES.includes(type)
+export const isBooleanValueType = (type) => BOOLEAN_VALUE_TYPES.includes(type)
From b5f9b79f0b33a625ada01a77da57baef8851dd22 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Wed, 26 Jun 2024 14:30:12 +0000
Subject: [PATCH 095/130] chore(release): cut 26.7.6 [skip ci]
## [26.7.6](https://github.com/dhis2/analytics/compare/v26.7.5...v26.7.6) (2024-06-26)
### Bug Fixes
* apply legend to all numeric and boolean types (DHIS2-17611) ([#1683](https://github.com/dhis2/analytics/issues/1683)) ([e93b106](https://github.com/dhis2/analytics/commit/e93b106f7e0b3ab9ebae8a21a07d5cebee3d48d3))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index a70157b76..843fa31fd 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.7.6](https://github.com/dhis2/analytics/compare/v26.7.5...v26.7.6) (2024-06-26)
+
+
+### Bug Fixes
+
+* apply legend to all numeric and boolean types (DHIS2-17611) ([#1683](https://github.com/dhis2/analytics/issues/1683)) ([e93b106](https://github.com/dhis2/analytics/commit/e93b106f7e0b3ab9ebae8a21a07d5cebee3d48d3))
+
## [26.7.5](https://github.com/dhis2/analytics/compare/v26.7.4...v26.7.5) (2024-06-25)
diff --git a/package.json b/package.json
index a437b7fda..3a4ddaac0 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.5",
+ "version": "26.7.6",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 3e5ece9b59f45c5902a882dedc40fd1c28322e8a Mon Sep 17 00:00:00 2001
From: Hendrik de Graaf
Date: Mon, 8 Jul 2024 14:29:30 +0200
Subject: [PATCH 096/130] fix: remove duplicate @dhis2/multi-calendar-dates
dependency (#1689)
---
yarn.lock | 11 +----------
1 file changed, 1 insertion(+), 10 deletions(-)
diff --git a/yarn.lock b/yarn.lock
index 1cc77afd3..26c33c90c 100644
--- a/yarn.lock
+++ b/yarn.lock
@@ -2454,16 +2454,7 @@
i18next "^10.3"
moment "^2.24.0"
-"@dhis2/multi-calendar-dates@^1.1.1":
- version "1.2.1"
- resolved "https://registry.yarnpkg.com/@dhis2/multi-calendar-dates/-/multi-calendar-dates-1.2.1.tgz#d31ac037302879ae624d72d2373ac455b7e357e8"
- integrity sha512-lIYwpDbHXKnquvkMDuT2E+V/MwjPDIPIfLi9xfWq5SkuZE3zSl0g65echWYySeZ7EzgRhrtYwA3nuWwuGfcV5Q==
- dependencies:
- "@dhis2/d2-i18n" "^1.1.3"
- "@js-temporal/polyfill" "0.4.3"
- classnames "^2.3.2"
-
-"@dhis2/multi-calendar-dates@^1.2.2":
+"@dhis2/multi-calendar-dates@^1.1.1", "@dhis2/multi-calendar-dates@^1.2.2":
version "1.2.2"
resolved "https://registry.yarnpkg.com/@dhis2/multi-calendar-dates/-/multi-calendar-dates-1.2.2.tgz#c34e5172474ddc73ad829515ed4c489fb8023669"
integrity sha512-Bl4y2+oDMJLZwtQ1Djfd+wJxOkGixBl6SCuLNH08B3RJSTwF/HcwgtY0vv7tcKUs63SwS7fK6ittXphyB4HJjQ==
From 77f42a0d500f59d5d7b718286b6bca11296f7c12 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Mon, 8 Jul 2024 12:33:08 +0000
Subject: [PATCH 097/130] chore(release): cut 26.7.7 [skip ci]
## [26.7.7](https://github.com/dhis2/analytics/compare/v26.7.6...v26.7.7) (2024-07-08)
### Bug Fixes
* remove duplicate @dhis2/multi-calendar-dates dependency ([#1689](https://github.com/dhis2/analytics/issues/1689)) ([3e5ece9](https://github.com/dhis2/analytics/commit/3e5ece9b59f45c5902a882dedc40fd1c28322e8a))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 843fa31fd..20dfb64c2 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.7.7](https://github.com/dhis2/analytics/compare/v26.7.6...v26.7.7) (2024-07-08)
+
+
+### Bug Fixes
+
+* remove duplicate @dhis2/multi-calendar-dates dependency ([#1689](https://github.com/dhis2/analytics/issues/1689)) ([3e5ece9](https://github.com/dhis2/analytics/commit/3e5ece9b59f45c5902a882dedc40fd1c28322e8a))
+
## [26.7.6](https://github.com/dhis2/analytics/compare/v26.7.5...v26.7.6) (2024-06-26)
diff --git a/package.json b/package.json
index 3a4ddaac0..f0eb8d2cb 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.6",
+ "version": "26.7.7",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From f2f516de181f6413061a1bfce5606d7575e5e1f5 Mon Sep 17 00:00:00 2001
From: Edoardo Sabadelli
Date: Fri, 12 Jul 2024 13:46:52 +0200
Subject: [PATCH 098/130] fix: do not call period generator with non-4-digit
year (DHIS2-17707) (#1690)
---
.../PeriodDimension/PeriodTransfer.js | 19 +++++++++++--------
1 file changed, 11 insertions(+), 8 deletions(-)
diff --git a/src/components/PeriodDimension/PeriodTransfer.js b/src/components/PeriodDimension/PeriodTransfer.js
index a660e6498..cd4095484 100644
--- a/src/components/PeriodDimension/PeriodTransfer.js
+++ b/src/components/PeriodDimension/PeriodTransfer.js
@@ -156,15 +156,18 @@ const PeriodTransfer = ({
const onSelectFixedPeriods = (filter) => {
setFixedFilter(filter)
- setAllPeriods(
- getFixedPeriodsOptionsById(
- filter.periodType,
- periodsSettings
- ).getPeriods(
- fixedPeriodConfig(Number(filter.year)),
- periodsSettings
+
+ if (filter.year.match(/[0-9]{4}/)) {
+ setAllPeriods(
+ getFixedPeriodsOptionsById(
+ filter.periodType,
+ periodsSettings
+ ).getPeriods(
+ fixedPeriodConfig(Number(filter.year)),
+ periodsSettings
+ )
)
- )
+ }
}
const renderEmptySelection = () => (
From e9f0b4730041132ad572d7d6b55ba0327c023aa9 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Fri, 12 Jul 2024 11:50:26 +0000
Subject: [PATCH 099/130] chore(release): cut 26.7.8 [skip ci]
## [26.7.8](https://github.com/dhis2/analytics/compare/v26.7.7...v26.7.8) (2024-07-12)
### Bug Fixes
* do not call period generator with non-4-digit year (DHIS2-17707) ([#1690](https://github.com/dhis2/analytics/issues/1690)) ([f2f516d](https://github.com/dhis2/analytics/commit/f2f516de181f6413061a1bfce5606d7575e5e1f5))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 20dfb64c2..47fcc88a7 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.7.8](https://github.com/dhis2/analytics/compare/v26.7.7...v26.7.8) (2024-07-12)
+
+
+### Bug Fixes
+
+* do not call period generator with non-4-digit year (DHIS2-17707) ([#1690](https://github.com/dhis2/analytics/issues/1690)) ([f2f516d](https://github.com/dhis2/analytics/commit/f2f516de181f6413061a1bfce5606d7575e5e1f5))
+
## [26.7.7](https://github.com/dhis2/analytics/compare/v26.7.6...v26.7.7) (2024-07-08)
diff --git a/package.json b/package.json
index f0eb8d2cb..5647defc7 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.7",
+ "version": "26.7.8",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 9bc81ab1bec16886ad48540f3a3828a97f841ce3 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Wed, 24 Jul 2024 03:39:50 +0200
Subject: [PATCH 100/130] fix(translations): sync translations from transifex
(master)
Automatically merged.
---
i18n/es_419.po | 743 ++++++++++++++++++++++++++-----------------------
1 file changed, 399 insertions(+), 344 deletions(-)
diff --git a/i18n/es_419.po b/i18n/es_419.po
index e3a15ca3c..9ea8454a5 100644
--- a/i18n/es_419.po
+++ b/i18n/es_419.po
@@ -6,7 +6,7 @@
msgid ""
msgstr ""
"Project-Id-Version: i18next-conv\n"
-"POT-Creation-Date: 2023-09-27T14:15:13.876Z\n"
+"POT-Creation-Date: 2024-06-26T14:09:30.876Z\n"
"PO-Revision-Date: 2020-04-28 22:05+0000\n"
"Last-Translator: Enzo Nicolas Rossi , 2024\n"
"Language-Team: Spanish (Latin America) (https://app.transifex.com/hisp-uio/teams/100509/es_419/)\n"
@@ -17,299 +17,321 @@ msgstr ""
"Plural-Forms: nplurals=3; plural=n == 1 ? 0 : n != 0 && n % 1000000 == 0 ? 1 : 2;\n"
msgid "view only"
-msgstr ""
+msgstr "ver sólo"
msgid "view and edit"
-msgstr ""
+msgstr "ver y editar"
msgid "all users ({{accessLevel}})"
-msgstr ""
+msgstr "todos los usuarios ({{accessLevel}})"
msgid "{{userOrGroup}} ({{accessLevel}})"
-msgstr ""
+msgstr "{{userOrGroup}} ({{accessLevel}})"
msgid "Shared with {{commaSeparatedListOfUsersAndGroups}}"
-msgstr ""
+msgstr "Compartido con {{commaSeparatedListOfUsersAndGroups}}"
msgid "Not shared with any users or groups"
-msgstr ""
+msgstr "No se comparte con ningún usuario o grupo"
msgid "No description"
-msgstr ""
+msgstr "Sin descripción"
msgid "Last updated {{time}}"
-msgstr ""
+msgstr "Última actualización {{time}}"
msgid "Created {{time}} by {{author}}"
-msgstr ""
+msgstr "Creado {{time}} por {{author}}"
msgid "Created {{time}}"
-msgstr ""
+msgstr "Creado {{time}}"
msgid "Viewed {{count}} times"
msgid_plural "Viewed {{count}} times"
-msgstr[0] ""
-msgstr[1] ""
-msgstr[2] ""
+msgstr[0] "Visto 1 vez"
+msgstr[1] "Visto {{count}} veces"
+msgstr[2] "Visto {{count}} veces"
msgid "Notifications"
-msgstr ""
+msgstr "Notificaciones"
msgid "You're subscribed and getting updates about new interpretations."
msgstr ""
+"Estás suscrito y recibes actualizaciones sobre nuevas interpretaciones."
msgid "Unsubscribe"
-msgstr ""
+msgstr "Cancelar suscripción"
msgid "Subscribe to get updates about new interpretations."
msgstr ""
+"Suscríbase para recibir información actualizada sobre nuevas "
+"interpretaciones."
msgid "Subscribe"
-msgstr ""
+msgstr "Suscríbase a"
msgid "About this map"
-msgstr ""
+msgstr "Acerca de este mapa"
msgid "About this line list"
-msgstr ""
+msgstr "Acerca de esta lista"
msgid "About this visualization"
-msgstr ""
+msgstr "Acerca de esta visualización"
msgid "This app could not retrieve required data."
-msgstr ""
+msgstr "Esta aplicación no pudo recuperar los datos requeridos."
msgid "Network error"
-msgstr ""
+msgstr "Error de red"
msgid "Data / Edit calculation"
-msgstr ""
+msgstr "Datos / Editar cálculo"
msgid "Data / New calculation"
-msgstr ""
+msgstr "Datos / Nuevo cálculo"
msgid "Remove item"
-msgstr ""
+msgstr "Quitar elemento"
msgid "Check formula"
-msgstr ""
+msgstr "Verificar fórmula"
msgid "Calculation name"
-msgstr ""
+msgstr "Nombre del cálculo"
msgid "Shown in table headers and chart axes/legends"
msgstr ""
+"Se muestra en los encabezados de las tablas y en los ejes/leyendas de los "
+"gráficos"
msgid "Delete calculation"
-msgstr ""
+msgstr "Borrar cálculo"
msgid "Cancel"
msgstr "Cancelar"
msgid "The calculation can only be saved with a valid formula"
-msgstr ""
+msgstr "El cálculo sólo puede guardarse con una fórmula válida"
msgid "Add a name to save this calculation"
-msgstr ""
+msgstr "Añada un nombre para guardar este cálculo"
msgid "Save calculation"
-msgstr ""
+msgstr "Guardar cálculo"
msgid ""
"Are you sure you want to delete this calculation? It may be used by other "
"visualizations."
msgstr ""
+"¿Está seguro de que desea eliminar este cálculo? Puede ser utilizado por "
+"otras visualizaciones."
msgid "Yes, delete"
-msgstr ""
+msgstr "Sí, borrar"
msgid "Totals only"
-msgstr ""
+msgstr "Sólo totales"
msgid "Details only"
-msgstr ""
+msgstr "Sólo detalles"
msgid "Loading"
-msgstr ""
+msgstr "Cargando"
msgid "Data elements"
-msgstr ""
+msgstr "Elementos de datos"
msgid "Search by data element name"
-msgstr ""
+msgstr "Búsqueda por nombre de elemento de datos"
msgid "No data elements found for \"{{- searchTerm}}\""
-msgstr ""
+msgstr "No se han encontrado datos para \"{{- searchTerm}}\""
msgid "No data elements found"
-msgstr ""
+msgstr "No se han encontrado datos"
msgid ""
"Drag items here, or double click in the list, to start building a "
"calculation formula"
msgstr ""
+"Arrastre los elementos aquí, o haga doble clic en la lista, para empezar a "
+"construir una fórmula de cálculo"
msgid "Math operators"
-msgstr ""
+msgstr "Operadores matemáticos"
msgid "Data Type"
-msgstr ""
+msgstr "Tipo de datos"
+
+msgid "Only {{dataType}} can be used in {{visType}}"
+msgstr "Sólo {{dataType}} puede utilizarse en {{visType}}"
msgid "All types"
-msgstr ""
+msgstr "Todos los tipos"
msgid "Disaggregation"
-msgstr ""
+msgstr "Desagregación"
msgid "No data"
msgstr "No hay datos"
msgid "Search by data item name"
-msgstr ""
+msgstr "Búsqueda por nombre de elemento de datos"
msgid "No items selected"
msgstr "No hay elementos seleccionados"
msgid "Selected Items"
-msgstr ""
+msgstr "Artículos seleccionados"
msgid "No indicators found"
-msgstr ""
+msgstr "No se han encontrado indicadores"
msgid "No data sets found"
-msgstr ""
+msgstr "No se han encontrado conjuntos de datos"
msgid "No event data items found"
-msgstr ""
+msgstr "No se han encontrado datos de eventos"
msgid "No program indicators found"
-msgstr ""
+msgstr "No se han encontrado indicadores de programa"
+
+msgid "No calculations found"
+msgstr "No se han encontrado cálculos"
msgid "No indicators found for \"{{- searchTerm}}\""
-msgstr ""
+msgstr "No se han encontrado indicadores para \"{{- searchTerm}}\""
msgid "No data sets found for \"{{- searchTerm}}\""
-msgstr ""
+msgstr "No se han encontrado conjuntos de datos para \"{{- searchTerm}}\""
msgid "No event data items found for \"{{- searchTerm}}\""
-msgstr ""
+msgstr "No se han encontrado datos de eventos para \"{{- searchTerm}}\""
msgid "No program indicators found for \"{{- searchTerm}}\""
-msgstr ""
+msgstr "No se han encontrado indicadores de programa para \"{{- searchTerm}}\""
+
+msgid "No calculations found for \"{{- searchTerm}}\""
+msgstr "No se han encontrado cálculos para \"{{- searchTerm}}\""
msgid "Nothing found for \"{{- searchTerm}}\""
-msgstr ""
+msgstr "No se ha encontrado nada para \"{{- searchTerm}}\""
msgid "Calculation"
-msgstr ""
+msgstr "Cálculo"
msgid "Metric type"
-msgstr ""
+msgstr "Tipo de métrica"
msgid "All metrics"
-msgstr ""
+msgstr "Todas las métricas"
msgid "Move to {{axisName}}"
-msgstr ""
+msgstr "Mover a {{axisName}}"
msgid "Add to {{axisName}}"
msgstr "Añadir a {{axisName}}"
msgid "Not available for {{visualizationType}}"
-msgstr ""
+msgstr "No disponible para {{visualizationType}}"
msgid "Remove Assigned Categories"
-msgstr ""
+msgstr "Eliminar categorías asignadas"
msgid "Add Assigned Categories"
-msgstr ""
+msgstr "Añadir categorías asignadas"
msgid "Remove"
msgstr "Eliminar"
msgid "Filter dimensions"
-msgstr ""
+msgstr "Dimensiones del filtro"
msgid "Main dimensions"
-msgstr ""
+msgstr "Dimensiones principales"
msgid "Your dimensions"
-msgstr ""
+msgstr "Sus dimensiones"
msgid "Dimension recommended with selected data"
-msgstr ""
+msgstr "Dimensión recomendada con datos seleccionados"
msgid "All items"
-msgstr ""
+msgstr "Todos los artículos"
msgid "Automatically include all items"
-msgstr ""
+msgstr "Incluir automáticamente todos los elementos"
msgid ""
"Select all {{- dimensionTitle}} items. With this option, new items added in "
"the future will be automatically included."
msgstr ""
+"Seleccionar todos los elementos {{- dimensionTitle}}. Con esta opción, los "
+"nuevos elementos que se añadan en el futuro se incluirán automáticamente."
msgid "Manually select items..."
-msgstr ""
+msgstr "Seleccionar elementos manualmente..."
msgid "Nothing found in {{- dimensionTitle}}"
-msgstr ""
+msgstr "No se ha encontrado nada en {{- dimensionTitle}}"
msgid "Search"
msgstr "Buscar"
msgid "Nothing found for {{- searchTerm}}"
-msgstr ""
+msgstr "No se ha encontrado nada para {{- searchTerm}}"
msgid "Delete {{fileType}}"
-msgstr ""
+msgstr "Borrar {{fileType}}"
msgid ""
"This {{fileType}} and related interpretations will be deleted. Continue?"
msgstr ""
+"Este {{fileType}} y las interpretaciones relacionadas serán eliminados. "
+"¿Continuar?"
msgid "Delete"
msgstr "Borrar"
msgid "File"
-msgstr ""
+msgstr "Archivo"
msgid "New"
msgstr "Nuevo"
msgid "Open…"
-msgstr ""
+msgstr "Abrir..."
msgid "Save"
msgstr "Guardar"
msgid "Save…"
-msgstr ""
+msgstr "Guardar..."
msgid "Save as…"
-msgstr ""
+msgstr "Guardar como..."
msgid "Rename…"
-msgstr ""
+msgstr "Renombrar..."
msgid "Translate…"
-msgstr ""
+msgstr "Traducir..."
msgid "Share…"
-msgstr ""
+msgstr "Compartir..."
msgid "Get link…"
-msgstr ""
+msgstr "Obtener enlace..."
msgid "Open in this app"
-msgstr ""
+msgstr "Abrir en esta aplicación"
msgid "Close"
msgstr "Cerrar"
msgid "Rename {{fileType}}"
-msgstr ""
+msgstr "Cambie el nombre de {{fileType}}"
msgid "Name"
msgstr "Nombre"
@@ -318,344 +340,338 @@ msgid "Description"
msgstr "Descripción"
msgid "Rename"
-msgstr ""
+msgstr "Cambie el nombre de"
msgid "{{- objectName}} (copy)"
-msgstr ""
+msgstr "{{- objectName}} (copia)"
msgid "Save {{fileType}} as"
-msgstr ""
+msgstr "Guardar {{fileType}} como"
msgid "event report"
-msgstr ""
+msgstr "informe del evento"
msgid "line list"
-msgstr ""
+msgstr "lista"
msgid "map"
-msgstr ""
+msgstr "mapa"
msgid "visualization"
-msgstr ""
+msgstr "visualización"
msgid "Edit"
-msgstr ""
+msgstr "Editar"
msgid "Write a reply"
-msgstr ""
+msgstr "Escribir una respuesta"
msgid "Post reply"
-msgstr ""
+msgstr "Respuesta"
msgid "Delete failed"
-msgstr ""
+msgstr "Eliminación fallida"
msgid "Could not update comment"
-msgstr ""
+msgstr "No se ha podido actualizar el comentario"
msgid "Enter comment text"
-msgstr ""
+msgstr "Introduzca el texto del comentario"
msgid "Update"
msgstr "Actualizar"
msgid "Viewing interpretation: {{- visualisationName}}"
-msgstr ""
+msgstr "Interpretación de la visualización: {{- visualisationName}}"
msgid "Could not load interpretation"
-msgstr ""
+msgstr "No se ha podido cargar la interpretación"
msgid ""
"The interpretation couldn’t be displayed. Try again or contact your system "
"administrator."
msgstr ""
+"No se ha podido mostrar la interpretación. Inténtelo de nuevo o póngase en "
+"contacto con el administrador del sistema."
msgid "Hide interpretation"
-msgstr ""
+msgstr "Ocultar interpretación"
msgid "Write an interpretation"
-msgstr ""
+msgstr "Escribir una interpretación"
msgid ""
"Other people viewing this interpretation in the future may see more data."
msgstr ""
+"Otras personas que vean esta interpretación en el futuro podrían ver más "
+"datos."
msgid "Post interpretation"
-msgstr ""
+msgstr "Interpretación de puestos"
msgid "Interpretations"
-msgstr ""
+msgstr "Interpretaciones"
msgid "Reply"
-msgstr ""
+msgstr "Respuesta"
msgid "{{count}} replies"
msgid_plural "{{count}} replies"
-msgstr[0] ""
-msgstr[1] ""
-msgstr[2] ""
+msgstr[0] "{{count}} respuesta"
+msgstr[1] "{{count}} responde"
+msgstr[2] "{{count}} responde"
msgid "View replies"
-msgstr ""
+msgstr "Ver respuestas"
msgid "Unlike"
-msgstr ""
+msgstr "A diferencia de"
msgid "Like"
-msgstr ""
+msgstr "Como"
+
+msgid "See interpretation"
+msgstr "Ver interpretación"
+
+msgid "Open in app"
+msgstr "Abrir en aplicación"
msgid "Share"
msgstr "Compartir"
-msgid "See interpretation"
-msgstr ""
-
msgid "Manage sharing"
-msgstr ""
+msgstr "Gestionar el uso compartido"
msgid "Could not update interpretation"
-msgstr ""
+msgstr "No se ha podido actualizar la interpretación"
msgid "Enter interpretation text"
-msgstr ""
-
-msgid "Bold text"
-msgstr ""
-
-msgid "Italic text"
-msgstr ""
-
-msgid "Link to a URL"
-msgstr ""
-
-msgid "Mention a user"
-msgstr ""
-
-msgid "Add emoji"
-msgstr ""
-
-msgid "Preview"
-msgstr ""
-
-msgid "Back to write mode"
-msgstr ""
-
-msgid "Too many results. Try refining the search."
-msgstr ""
-
-msgid "Search for a user"
-msgstr ""
-
-msgid "Searching for \"{{- searchText}}\""
-msgstr ""
-
-msgid "No results found"
-msgstr "No se han encontrado resultados"
+msgstr "Introducir texto de interpretación"
msgid "Not available offline"
-msgstr ""
+msgstr "No disponible sin conexión"
msgid "Created by"
-msgstr ""
+msgstr "Creado por"
msgid "Anyone"
msgstr "Quien sea"
msgid "Only you"
-msgstr ""
+msgstr "Sólo tú"
msgid "Others"
-msgstr ""
+msgstr "Otros"
msgid "Not supported by this app yet"
-msgstr ""
+msgstr "Esta aplicación aún no es compatible"
msgid "Filter by name"
-msgstr ""
+msgstr "Filtrar por nombre"
msgid "Created"
-msgstr ""
+msgstr "Creado"
msgid "Last updated"
msgstr "Última actualización"
msgid "Type"
-msgstr ""
+msgstr "Tipo"
msgid "Clear filters"
msgstr "Limpiar filtros"
msgid "{{firstItemIndex}}-{{lastItemIndex}} of {{totalNumberOfItems}}"
-msgstr ""
+msgstr "{{firstItemIndex}}-{{lastItemIndex}} de {{totalNumberOfItems}}"
msgid "Open"
msgstr "Abierto"
msgid "Couldn't load items"
-msgstr ""
+msgstr "No se pueden cargar los artículos"
msgid ""
"There was a problem loading items. Try again or contact your system "
"administrator."
msgstr ""
+"Se ha producido un problema al cargar los artículos. Inténtelo de nuevo o "
+"póngase en contacto con el administrador del sistema."
msgid "No items found. Create a new to get started."
-msgstr ""
+msgstr "No se han encontrado artículos. Crea uno nuevo para empezar."
msgid ""
"No items found. Try adjusting your search or filter options to find what "
"you're looking for."
msgstr ""
+"No se han encontrado artículos. Prueba a ajustar las opciones de búsqueda o "
+"filtro para encontrar lo que buscas."
msgid "Create new"
msgstr "Crear nuevo"
msgid "Open a visualization"
-msgstr ""
+msgstr "Abrir una visualización"
msgid "Loading visualizations"
-msgstr ""
+msgstr "Cargando visualizaciones"
msgid "Couldn't load visualizations"
-msgstr ""
+msgstr "No se pueden cargar las visualizaciones"
msgid ""
"There was a problem loading visualizations. Try again or contact your system"
" administrator."
msgstr ""
+"Se ha producido un problema al cargar las visualizaciones. Inténtelo de "
+"nuevo o póngase en contacto con el administrador del sistema."
msgid "No visualizations found. Click New visualization to get started."
msgstr ""
+"No se han encontrado visualizaciones. Haga clic en Nueva visualización para "
+"empezar."
msgid ""
"No visualizations found. Try adjusting your search or filter options to find"
" what you're looking for."
msgstr ""
+"No se han encontrado visualizaciones. Prueba a ajustar las opciones de "
+"búsqueda o filtro para encontrar lo que buscas."
msgid "New visualization"
-msgstr ""
+msgstr "Nueva visualización"
msgid "Open a map"
-msgstr ""
+msgstr "Abrir un mapa"
msgid "Loading maps"
-msgstr ""
+msgstr "Cargando mapas"
msgid "Couldn't load maps"
-msgstr ""
+msgstr "No se pueden cargar los mapas"
msgid ""
"There was a problem loading maps. Try again or contact your system "
"administrator."
msgstr ""
+"Se ha producido un problema al cargar los mapas. Inténtalo de nuevo o ponte "
+"en contacto con el administrador del sistema."
msgid "No maps found. Click New map to get started."
-msgstr ""
+msgstr "No se han encontrado mapas. Haga clic en Nuevo mapa para empezar."
msgid ""
"No maps found. Try adjusting your search or filter options to find what "
"you're looking for."
msgstr ""
+"No se han encontrado mapas. Prueba a ajustar las opciones de búsqueda o "
+"filtro para encontrar lo que buscas."
msgid "New map"
-msgstr ""
+msgstr "Nuevo mapa"
msgid "Open a line list"
-msgstr ""
+msgstr "Abrir una lista"
msgid "Loading line lists"
-msgstr ""
+msgstr "Carga de listas de líneas"
msgid "Couldn't load line lists"
-msgstr ""
+msgstr "No se pueden cargar las listas"
msgid ""
"There was a problem loading line lists. Try again or contact your system "
"administrator."
msgstr ""
+"Se ha producido un problema al cargar las listas. Inténtelo de nuevo o "
+"póngase en contacto con el administrador del sistema."
msgid "No line lists found. Click New line list to get started."
msgstr ""
+"No se ha encontrado ninguna lista. Haga clic en Nueva lista de líneas para "
+"empezar."
msgid ""
"No line lists found. Try adjusting your search or filter options to find "
"what you're looking for."
msgstr ""
+"No se han encontrado listas. Prueba a ajustar las opciones de búsqueda o "
+"filtro para encontrar lo que buscas."
msgid "New line list"
-msgstr ""
+msgstr "Nueva lista"
msgid "Options"
-msgstr ""
+msgstr "Opciones"
msgid "Hide"
-msgstr ""
+msgstr "Ocultar"
msgid "{{count}} org units"
msgid_plural "{{count}} org units"
-msgstr[0] ""
-msgstr[1] ""
-msgstr[2] ""
+msgstr[0] "{{count}} unidad org"
+msgstr[1] "{{count}} unidades org"
+msgstr[2] "{{count}} unidades org"
msgid "{{count}} levels"
msgid_plural "{{count}} levels"
-msgstr[0] ""
-msgstr[1] ""
-msgstr[2] ""
+msgstr[0] "{{count}} nivel"
+msgstr[1] "{{count}} niveles"
+msgstr[2] "{{count}} niveles"
msgid "{{count}} groups"
msgid_plural "{{count}} groups"
-msgstr[0] ""
-msgstr[1] ""
-msgstr[2] ""
+msgstr[0] "{{count}} grupo"
+msgstr[1] "{{count}} grupos"
+msgstr[2] "{{count}} grupos"
msgid "Selected: {{commaSeparatedListOfOrganisationUnits}}"
-msgstr ""
+msgstr "Seleccionado: {{commaSeparatedListOfOrganisationUnits}}"
msgid "Nothing selected"
-msgstr ""
+msgstr "Nada seleccionado"
msgid "User organisation unit"
-msgstr ""
+msgstr "Unidad organizativa del usuario"
msgid "User sub-units"
-msgstr ""
+msgstr "Subunidades de usuario"
msgid "User sub-x2-units"
-msgstr ""
+msgstr "Subunidadesx2 de usuario"
msgid "Select a level"
-msgstr ""
+msgstr "Seleccione un nivel"
msgid "Select a group"
-msgstr ""
+msgstr "Seleccione un grupo"
msgid "Deselect all"
-msgstr ""
+msgstr "Deseleccionar todo"
msgid "Period type"
-msgstr ""
+msgstr "Tipo de período"
msgid "Year"
-msgstr ""
+msgstr "Año"
msgid "Select year"
-msgstr ""
+msgstr "Seleccione el año"
msgid "Period"
msgstr "Periodo"
+msgid "Selected Periods"
+msgstr "Períodos seleccionados"
+
msgid "Relative periods"
-msgstr ""
+msgstr "Periodos relativos"
msgid "Fixed periods"
-msgstr ""
-
-msgid "Selected Periods"
-msgstr ""
+msgstr "Periodos fijos"
msgid "No periods selected"
-msgstr ""
+msgstr "No hay periodos seleccionados"
msgid "Daily"
msgstr "Diario"
@@ -664,49 +680,49 @@ msgid "Weekly"
msgstr "Semanal"
msgid "Weekly (Start Wednesday)"
-msgstr ""
+msgstr "Semanal (Inicio miércoles)"
msgid "Weekly (Start Thursday)"
-msgstr ""
+msgstr "Semanal (Inicio jueves)"
msgid "Weekly (Start Saturday)"
-msgstr ""
+msgstr "Semanal (inicio el sábado)"
msgid "Weekly (Start Sunday)"
-msgstr ""
+msgstr "Semanal (Inicio el domingo)"
msgid "Bi-weekly"
-msgstr ""
+msgstr "Cada dos semanas"
msgid "Monthly"
msgstr "Mensual"
msgid "Bi-monthly"
-msgstr ""
+msgstr "Bimensual"
msgid "Quarterly"
-msgstr ""
+msgstr "Trimestral"
msgid "Six-monthly"
-msgstr ""
+msgstr "Semestral"
msgid "Six-monthly April"
-msgstr ""
+msgstr "Semestral Abril"
msgid "Yearly"
msgstr "Anual"
msgid "Financial year (Start November)"
-msgstr ""
+msgstr "Ejercicio financiero (Inicio en noviembre)"
msgid "Financial year (Start October)"
-msgstr ""
+msgstr "Ejercicio financiero (Inicio en octubre)"
msgid "Financial year (Start July)"
-msgstr ""
+msgstr "Ejercicio financiero (inicio en julio)"
msgid "Financial year (Start April)"
-msgstr ""
+msgstr "Ejercicio financiero (Inicio en abril)"
msgid "Today"
msgstr "Hoy"
@@ -715,25 +731,25 @@ msgid "Yesterday"
msgstr "Ayer"
msgid "Last 3 days"
-msgstr ""
+msgstr "Últimos 3 días"
msgid "Last 7 days"
-msgstr ""
+msgstr "Últimos 7 días"
msgid "Last 14 days"
-msgstr ""
+msgstr "Últimos 14 días"
msgid "Last 30 days"
-msgstr ""
+msgstr "Últimos 30 días"
msgid "Last 60 days"
-msgstr ""
+msgstr "Últimos 60 días"
msgid "Last 90 days"
-msgstr ""
+msgstr "Últimos 90 días"
msgid "Last 180 days"
-msgstr ""
+msgstr "Últimos 180 días"
msgid "This week"
msgstr "Esta semana"
@@ -742,25 +758,25 @@ msgid "Last week"
msgstr "Última semana"
msgid "Last 4 weeks"
-msgstr ""
+msgstr "Últimas 4 semanas"
msgid "Last 12 weeks"
-msgstr ""
+msgstr "Últimas 12 semanas"
msgid "Last 52 weeks"
-msgstr ""
+msgstr "Últimas 52 semanas"
msgid "Weeks this year"
msgstr "Semanas de este año"
msgid "This bi-week"
-msgstr ""
+msgstr "Esta quincena"
msgid "Last bi-week"
-msgstr ""
+msgstr "Última quincena"
msgid "Last 4 bi-weeks"
-msgstr ""
+msgstr "Últimas 4 bisemanas"
msgid "This month"
msgstr "Este mes"
@@ -772,25 +788,25 @@ msgid "Last 3 months"
msgstr "Últimos 3 meses"
msgid "Last 6 months"
-msgstr ""
+msgstr "Últimos 6 meses"
msgid "Last 12 months"
-msgstr ""
+msgstr "Últimos 12 meses"
msgid "Months this year"
msgstr "Meses este año"
msgid "This bi-month"
-msgstr ""
+msgstr "Este bimestre"
msgid "Last bi-month"
-msgstr ""
+msgstr "Último bimestre"
msgid "Last 6 bi-months"
-msgstr ""
+msgstr "Últimos 6 bimestres"
msgid "Bi-months this year"
-msgstr ""
+msgstr "Bimensuales este año"
msgid "This quarter"
msgstr "Este trimestre"
@@ -799,19 +815,19 @@ msgid "Last quarter"
msgstr "El trimestre pasado"
msgid "Last 4 quarters"
-msgstr ""
+msgstr "Últimos 4 trimestres"
msgid "Quarters this year"
msgstr "Trimestres de este año"
msgid "This six-month"
-msgstr ""
+msgstr "Estos seis meses"
msgid "Last six-month"
-msgstr ""
+msgstr "Últimos seis meses"
msgid "Last 2 six-month"
-msgstr ""
+msgstr "Últimos 2 semestres"
msgid "This financial year"
msgstr "Este año fiscal"
@@ -820,7 +836,7 @@ msgid "Last financial year"
msgstr "Último ejercicio financiero"
msgid "Last 5 financial years"
-msgstr ""
+msgstr "Últimos 5 ejercicios"
msgid "This year"
msgstr "Este año"
@@ -829,10 +845,10 @@ msgid "Last year"
msgstr "El año pasado"
msgid "Last 5 years"
-msgstr ""
+msgstr "Últimos 5 años"
msgid "Last 10 years"
-msgstr ""
+msgstr "Últimos 10 años"
msgid "Days"
msgstr "Días"
@@ -841,262 +857,298 @@ msgid "Weeks"
msgstr "Semanas"
msgid "Bi-weeks"
-msgstr ""
+msgstr "Dos semanas"
msgid "Months"
msgstr "Meses"
msgid "Bi-months"
-msgstr ""
+msgstr "Bimensual"
msgid "Quarters"
-msgstr ""
+msgstr "Cuartos"
msgid "Six-months"
-msgstr ""
+msgstr "Seis meses"
msgid "Financial Years"
-msgstr ""
+msgstr "Ejercicios financieros"
msgid "Years"
msgstr "Años"
+msgid "Bold text"
+msgstr "Texto en negrita"
+
+msgid "Italic text"
+msgstr "Texto en cursiva"
+
+msgid "Link to a URL"
+msgstr "Enlace a una URL"
+
+msgid "Mention a user"
+msgstr "Mencionar a un usuario"
+
+msgid "Add emoji"
+msgstr "Añadir emoji"
+
+msgid "Preview"
+msgstr "Vista previa"
+
+msgid "Back to write mode"
+msgstr "Volver al modo de escritura"
+
msgid "Interpretations and details"
-msgstr ""
+msgstr "Interpretaciones y detalles"
msgid "Translating to"
-msgstr ""
+msgstr "Traducir a"
msgid "Choose a locale"
-msgstr ""
+msgstr "Elija una localidad"
msgid "Base locale reference"
-msgstr ""
+msgstr "Referencia de la configuración regional básica"
msgid "Choose a locale to translate from the menu above"
msgstr ""
+"Elija la configuración regional que desee traducir en el menú superior"
msgid "Translate: {{objectName}}"
-msgstr ""
+msgstr "Traduce: {{objectName}}"
msgid "Save translations"
-msgstr ""
+msgstr "Guardar traducciones"
msgid "Cannot save while offline"
-msgstr ""
+msgstr "No se puede guardar sin conexión"
msgid "Could not load translations"
-msgstr ""
+msgstr "No se han podido cargar las traducciones"
msgid "Retry"
-msgstr ""
+msgstr "Reintentar"
+
+msgid "Too many results. Try refining the search."
+msgstr "Demasiados resultados. Intenta refinar la búsqueda."
+
+msgid "Search for a user"
+msgstr "Buscar un usuario"
+
+msgid "Searching for \"{{- searchText}}\""
+msgstr "Buscando \"{{- searchText}}\""
+
+msgid "No results found"
+msgstr "No se han encontrado resultados"
msgid "Series"
-msgstr ""
+msgstr "Serie"
msgid "Category"
-msgstr ""
+msgstr "Categoría"
msgid "Filter"
-msgstr ""
+msgstr "Filtro"
msgid "Columns"
-msgstr ""
+msgstr "Columnas"
msgid "Rows"
-msgstr ""
+msgstr "Filas"
msgid "Points"
-msgstr ""
+msgstr "Puntos"
msgid "Reporting rate"
-msgstr ""
+msgstr "Índice de notificación"
msgid "Reporting rate on time"
-msgstr ""
+msgstr "Tasa de notificación puntual"
msgid "Actual reports"
-msgstr ""
+msgstr "Informes reales"
msgid "Actual reports on time"
-msgstr ""
+msgstr "Informes reales a tiempo"
msgid "Expected reports"
-msgstr ""
+msgstr "Informes previstos"
msgid "Program"
msgstr "Programa"
msgid "Select a program"
-msgstr ""
+msgstr "Seleccione un programa"
msgid "Indicators"
msgstr "Indicadores"
msgid "Indicator group"
-msgstr ""
+msgstr "Grupo de indicadores"
msgid "All groups"
-msgstr ""
+msgstr "Todos los grupos"
msgid "Indicator"
-msgstr ""
+msgstr "Indicador"
msgid "No indicator groups found"
-msgstr ""
+msgstr "No se han encontrado grupos de indicadores"
msgid "Loading indicator groups"
-msgstr ""
+msgstr "Grupos de indicadores de carga"
msgid "Data element group"
-msgstr ""
+msgstr "Grupo de elementos de datos"
msgid "Data element"
-msgstr ""
+msgstr "Elemento de datos"
msgid "No data element groups found"
-msgstr ""
+msgstr "No se han encontrado grupos de elementos de datos"
msgid "Loading data element groups"
-msgstr ""
+msgstr "Carga de grupos de elementos de datos"
msgid "Data sets"
msgstr "Sets de datos"
msgid "Data set"
-msgstr ""
+msgstr "Conjunto de datos"
msgid "All data sets"
-msgstr ""
+msgstr "Todos los conjuntos de datos"
msgid "Loading data sets"
-msgstr ""
+msgstr "Carga de conjuntos de datos"
msgid "Event data items"
-msgstr ""
+msgstr "Datos del evento"
msgid "All programs"
-msgstr ""
+msgstr "Todos los programas"
msgid "Event data item"
-msgstr ""
+msgstr "Datos del evento"
msgid "No programs found"
-msgstr ""
+msgstr "No se han encontrado programas"
msgid "Loading programs"
-msgstr ""
+msgstr "Carga de programas"
msgid "Program indicators"
-msgstr ""
+msgstr "Indicadores del programa"
msgid "Program indicator"
-msgstr ""
+msgstr "Indicador de programa"
msgid "Calculations"
-msgstr ""
+msgstr "Cálculos"
msgid "Number"
-msgstr ""
+msgstr "Número"
msgid "Formula is empty. Add items to the formula from the lists on the left."
msgstr ""
+"La fórmula está vacía. Añada elementos a la fórmula desde las listas de la "
+"izquierda."
msgid "Consecutive math operators"
-msgstr ""
+msgstr "Operadores matemáticos consecutivos"
msgid "Consecutive data elements"
-msgstr ""
+msgstr "Elementos de datos consecutivos"
msgid "Starts or ends with a math operator"
-msgstr ""
+msgstr "Comienza o termina con un operador matemático"
msgid "Empty parentheses"
-msgstr ""
+msgstr "Paréntesis vacíos"
msgid "Missing right parenthesis )"
-msgstr ""
+msgstr "Falta el paréntesis derecho )"
msgid "Missing left parenthesis ("
-msgstr ""
+msgstr "Falta el paréntesis izquierdo ("
msgid "Extra Small"
-msgstr ""
+msgstr "Extra pequeña"
msgid "Small"
-msgstr ""
+msgstr "Pequeña"
msgid "Regular"
-msgstr ""
+msgstr "Regular"
msgid "Large"
-msgstr ""
+msgstr "Grande"
msgid "Extra Large"
-msgstr ""
+msgstr "Extra grande"
msgid "Left"
-msgstr ""
+msgstr "Izquierda"
msgid "Center"
-msgstr ""
+msgstr "Centro"
msgid "Right"
-msgstr ""
+msgstr "Derecha"
msgid "Start"
-msgstr ""
+msgstr "Inicio"
msgid "Middle"
-msgstr ""
+msgstr "Medio"
msgid "End"
-msgstr ""
+msgstr "Fin"
msgid "Top"
-msgstr ""
+msgstr "Top"
msgid "Bottom"
-msgstr ""
+msgstr "Fondo"
msgid "{{dynamicOuNames}} and {{lastOuName}}"
-msgstr ""
+msgstr "{{dynamicOuNames}} y {{lastOuName}}"
msgid "{{allDynamicOuNames}} levels"
-msgstr ""
+msgstr "{{allDynamicOuNames}} niveles"
msgid "{{allDynamicOuNames}} groups"
-msgstr ""
+msgstr "{{allDynamicOuNames}} grupos"
msgid "{{allDynamicOuNames}} levels in {{staticOuNames}}"
-msgstr ""
+msgstr "{{allDynamicOuNames}} niveles en {{staticOuNames}}"
msgid "{{allDynamicOuNames}} groups in {{staticOuNames}}"
-msgstr ""
+msgstr "{{allDynamicOuNames}} grupos en {{staticOuNames}}"
msgid "{{percentage}}% of total x values"
-msgstr ""
+msgstr "{{percentage}}% del total de valores x"
msgid "{{percentage}}% of total y values"
-msgstr ""
+msgstr "{{percentage}}% del total de valores y"
msgid "{{thresholdFactor}} × IQR Q1"
-msgstr ""
+msgstr "{{thresholdFactor}} × IQR Q1"
msgid "{{thresholdFactor}} × IQR Q3"
-msgstr ""
+msgstr "{{thresholdFactor}} × IQR Q3"
msgid "{{thresholdFactor}} × Modified Z-score low"
-msgstr ""
+msgstr "{{thresholdFactor}} × Puntuación Z modificada baja"
msgid "{{thresholdFactor}} × Modified Z-score high"
-msgstr ""
+msgstr "{{thresholdFactor}} × Puntuación Z modificada alta"
msgid "{{thresholdFactor}} × Z-score low"
-msgstr ""
+msgstr "{{thresholdFactor}} × Puntuación Z baja"
msgid "{{thresholdFactor}} × Z-score high"
-msgstr ""
+msgstr "{{thresholdFactor}} × Puntuación Z alta"
msgid "Data"
msgstr "Datos"
@@ -1105,88 +1157,91 @@ msgid "Organisation unit"
msgstr "Unidad organizativa"
msgid "Assigned Categories"
-msgstr ""
+msgstr "Categorías asignadas"
msgid "Pivot table"
-msgstr ""
+msgstr "Tabla dinámica"
msgid "Area"
msgstr "Área"
msgid "Stacked area"
-msgstr ""
+msgstr "Área apilada"
msgid "Bar"
-msgstr ""
+msgstr "Bar"
msgid "Stacked bar"
-msgstr ""
+msgstr "Barra apilada"
msgid "Column"
msgstr "Columna"
msgid "Year over year (column)"
-msgstr ""
+msgstr "Año sobre año (columna)"
msgid "Stacked column"
-msgstr ""
+msgstr "Columna apilada"
msgid "Gauge"
-msgstr ""
+msgstr "Indicador"
msgid "Line"
-msgstr ""
+msgstr "Línea"
msgid "Line list"
-msgstr ""
+msgstr "Lista de líneas"
msgid "Year over year (line)"
-msgstr ""
+msgstr "Año sobre año (línea)"
msgid "Pie"
-msgstr ""
+msgstr "Pastel"
msgid "Radar"
-msgstr ""
+msgstr "Radar"
msgid "Scatter"
-msgstr ""
+msgstr "Dispersión"
msgid "Single value"
-msgstr ""
+msgstr "Valor único"
+
+msgid "Outlier table"
+msgstr "Tabla de valores atípicos"
msgid "All charts"
-msgstr ""
+msgstr "Todos los gráficos"
msgid "{{seriesName}} (trend)"
-msgstr ""
+msgstr "{{seriesName}} (tendencia)"
msgid "Trend"
-msgstr ""
+msgstr "Tendencia"
msgid "No legend for this series"
-msgstr ""
+msgstr "No hay leyenda para esta serie"
msgid "and {{amount}} more..."
-msgstr ""
+msgstr "y {{amount}} más..."
msgid "Linear Regression"
-msgstr ""
+msgstr "Regresión lineal"
msgid "Target"
-msgstr ""
+msgstr "Objetivo"
msgid "Base"
-msgstr ""
+msgstr "Base"
msgid "Axis {{axisId}}"
-msgstr ""
+msgstr "Eje {{axisId}}"
msgid "{{count}} items"
msgid_plural "{{count}} items"
-msgstr[0] ""
-msgstr[1] ""
-msgstr[2] ""
+msgstr[0] "{{count}} artículo"
+msgstr[1] "{{count}} artículos"
+msgstr[2] "{{count}} artículos"
msgid "Reset zoom"
-msgstr ""
+msgstr "Restablecer zoom"
From 39f107d564e49f9e9960830e541a1bf4e3b9ba1f Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Wed, 24 Jul 2024 01:43:27 +0000
Subject: [PATCH 101/130] chore(release): cut 26.7.9 [skip ci]
## [26.7.9](https://github.com/dhis2/analytics/compare/v26.7.8...v26.7.9) (2024-07-24)
### Bug Fixes
* **translations:** sync translations from transifex (master) ([9bc81ab](https://github.com/dhis2/analytics/commit/9bc81ab1bec16886ad48540f3a3828a97f841ce3))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 47fcc88a7..187b19bb4 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.7.9](https://github.com/dhis2/analytics/compare/v26.7.8...v26.7.9) (2024-07-24)
+
+
+### Bug Fixes
+
+* **translations:** sync translations from transifex (master) ([9bc81ab](https://github.com/dhis2/analytics/commit/9bc81ab1bec16886ad48540f3a3828a97f841ce3))
+
## [26.7.8](https://github.com/dhis2/analytics/compare/v26.7.7...v26.7.8) (2024-07-12)
diff --git a/package.json b/package.json
index 5647defc7..6c327623b 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.8",
+ "version": "26.7.9",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From ef6f6ab9a94b427af71c36af9f004c95660d8221 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jan=20Henrik=20=C3=98verland?=
Date: Thu, 1 Aug 2024 10:52:11 +0200
Subject: [PATCH 102/130] feat: pivot table as default vis type in DV (#1694)
---
src/modules/visTypes.js | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/src/modules/visTypes.js b/src/modules/visTypes.js
index 2040dad5e..bd7a9b37a 100644
--- a/src/modules/visTypes.js
+++ b/src/modules/visTypes.js
@@ -141,7 +141,7 @@ const legendSetTypes = [
VIS_TYPE_STACKED_BAR,
]
-export const defaultVisType = VIS_TYPE_COLUMN
+export const defaultVisType = VIS_TYPE_PIVOT_TABLE
export const isStacked = (type) => stackedTypes.includes(type)
export const isYearOverYear = (type) => yearOverYearTypes.includes(type)
export const isDualAxisType = (type) => dualAxisTypes.includes(type)
From c3acdffc93440245b3d0e5824cb0c48706420e11 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Thu, 1 Aug 2024 08:55:52 +0000
Subject: [PATCH 103/130] chore(release): cut 26.8.0 [skip ci]
# [26.8.0](https://github.com/dhis2/analytics/compare/v26.7.9...v26.8.0) (2024-08-01)
### Features
* pivot table as default vis type in DV ([#1694](https://github.com/dhis2/analytics/issues/1694)) ([ef6f6ab](https://github.com/dhis2/analytics/commit/ef6f6ab9a94b427af71c36af9f004c95660d8221))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 187b19bb4..8a5d9e32b 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+# [26.8.0](https://github.com/dhis2/analytics/compare/v26.7.9...v26.8.0) (2024-08-01)
+
+
+### Features
+
+* pivot table as default vis type in DV ([#1694](https://github.com/dhis2/analytics/issues/1694)) ([ef6f6ab](https://github.com/dhis2/analytics/commit/ef6f6ab9a94b427af71c36af9f004c95660d8221))
+
## [26.7.9](https://github.com/dhis2/analytics/compare/v26.7.8...v26.7.9) (2024-07-24)
diff --git a/package.json b/package.json
index 6c327623b..cd4f59bc5 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.7.9",
+ "version": "26.8.0",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 80c93068991aee21556f12960567cca7b594a324 Mon Sep 17 00:00:00 2001
From: =?UTF-8?q?Jan=20Henrik=20=C3=98verland?=
Date: Thu, 8 Aug 2024 12:44:08 +0200
Subject: [PATCH 104/130] fix: sort analytics request params and items for
cache hit optimization (DHIS2-17861) (#1695)
Relevant apps: DV
---
src/api/analytics/AnalyticsBase.js | 27 ++++++++++---------
.../analytics/__tests__/AnalyticsBase.spec.js | 2 +-
2 files changed, 16 insertions(+), 13 deletions(-)
diff --git a/src/api/analytics/AnalyticsBase.js b/src/api/analytics/AnalyticsBase.js
index 9d5d82cff..3bd153818 100644
--- a/src/api/analytics/AnalyticsBase.js
+++ b/src/api/analytics/AnalyticsBase.js
@@ -27,8 +27,12 @@ const analyticsDataQuery = {
}),
params: ({ dimensions, filters, parameters }) => {
return {
- dimension: dimensions.length ? dimensions : undefined,
- filter: filters.length ? filters : undefined,
+ dimension: dimensions.length
+ ? generateDimensionStrings(dimensions, { sorted: true })
+ : undefined,
+ filter: filters.length
+ ? generateDimensionStrings(filters, { sorted: true })
+ : undefined,
...parameters,
skipMeta: true,
skipData: false,
@@ -45,8 +49,10 @@ const analyticsMetaDataQuery = {
trackedEntityType,
}),
params: ({ dimensions, filters, parameters }) => ({
- dimension: dimensions.length ? dimensions : undefined,
- filter: filters.length ? filters : undefined,
+ dimension: dimensions.length
+ ? generateDimensionStrings(dimensions)
+ : undefined,
+ filter: filters.length ? generateDimensionStrings(filters) : undefined,
...parameters,
skipMeta: false,
skipData: true,
@@ -55,14 +61,11 @@ const analyticsMetaDataQuery = {
}
export const generateDimensionStrings = (dimensions = [], options) => {
- if (options && options.sorted) {
- dimensions = sortBy(dimensions, 'dimension')
- }
-
- return dimensions.map(({ dimension, items }) => {
+ const sortedDimensions = sortBy(dimensions, 'dimension')
+ return sortedDimensions.map(({ dimension, items }) => {
if (Array.isArray(items) && items.length) {
if (options && options.sorted) {
- items.sort()
+ items = items.slice().sort()
}
return `${dimension}:${items.join(';')}`
@@ -131,8 +134,8 @@ class AnalyticsBase {
path: req.path,
program: req.program,
trackedEntityType: req.trackedEntityType,
- dimensions: generateDimensionStrings(req.dimensions),
- filters: generateDimensionStrings(req.filters),
+ dimensions: req.dimensions,
+ filters: req.filters,
parameters: req.parameters,
dataParams: dataReq.parameters,
metaDataParams: metaDataReq.parameters,
diff --git a/src/api/analytics/__tests__/AnalyticsBase.spec.js b/src/api/analytics/__tests__/AnalyticsBase.spec.js
index c5d3fb1d8..9bc51eae6 100644
--- a/src/api/analytics/__tests__/AnalyticsBase.spec.js
+++ b/src/api/analytics/__tests__/AnalyticsBase.spec.js
@@ -33,7 +33,7 @@ describe('generateDimensionString', () => {
items: ['item1'],
},
],
- output: ['dim2:item2;item1', 'dim1:item1'],
+ output: ['dim1:item1', 'dim2:item2;item1'],
outputSorted: ['dim1:item1', 'dim2:item1;item2'],
},
]
From 59f717eec043702cb35f99ab70e321eec1240d25 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Thu, 8 Aug 2024 10:47:49 +0000
Subject: [PATCH 105/130] chore(release): cut 26.8.1 [skip ci]
## [26.8.1](https://github.com/dhis2/analytics/compare/v26.8.0...v26.8.1) (2024-08-08)
### Bug Fixes
* sort analytics request params and items for cache hit optimization (DHIS2-17861) ([#1695](https://github.com/dhis2/analytics/issues/1695)) ([80c9306](https://github.com/dhis2/analytics/commit/80c93068991aee21556f12960567cca7b594a324))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 8a5d9e32b..3d56447e4 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.8.1](https://github.com/dhis2/analytics/compare/v26.8.0...v26.8.1) (2024-08-08)
+
+
+### Bug Fixes
+
+* sort analytics request params and items for cache hit optimization (DHIS2-17861) ([#1695](https://github.com/dhis2/analytics/issues/1695)) ([80c9306](https://github.com/dhis2/analytics/commit/80c93068991aee21556f12960567cca7b594a324))
+
# [26.8.0](https://github.com/dhis2/analytics/compare/v26.7.9...v26.8.0) (2024-08-01)
diff --git a/package.json b/package.json
index cd4f59bc5..ab86e2261 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.8.0",
+ "version": "26.8.1",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From efff1c81845a974fe8c60b593e6bbe42c19682d7 Mon Sep 17 00:00:00 2001
From: Jen Jones Arnesen
Date: Tue, 27 Aug 2024 13:44:20 +0200
Subject: [PATCH 106/130] fix: add AO TYPE for event chart and event report
(#1697)
Fixes DHIS2-17943
eventCharts and eventReports were missing in the list of AO_TYPES, causing the
AboutAoUnit component to break.
---
i18n/en.pot | 10 ++++++++--
src/components/AboutAOUnit/utils.js | 14 ++++++++++++++
2 files changed, 22 insertions(+), 2 deletions(-)
diff --git a/i18n/en.pot b/i18n/en.pot
index 7aea739a6..2e98715e2 100644
--- a/i18n/en.pot
+++ b/i18n/en.pot
@@ -5,8 +5,8 @@ msgstr ""
"Content-Type: text/plain; charset=utf-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=(n != 1)\n"
-"POT-Creation-Date: 2024-06-26T14:09:30.876Z\n"
-"PO-Revision-Date: 2024-06-26T14:09:30.876Z\n"
+"POT-Creation-Date: 2024-08-27T11:29:09.031Z\n"
+"PO-Revision-Date: 2024-08-27T11:29:09.033Z\n"
msgid "view only"
msgstr "view only"
@@ -67,6 +67,12 @@ msgstr "About this line list"
msgid "About this visualization"
msgstr "About this visualization"
+msgid "About this event chart"
+msgstr "About this event chart"
+
+msgid "About this event report"
+msgstr "About this event report"
+
msgid "This app could not retrieve required data."
msgstr "This app could not retrieve required data."
diff --git a/src/components/AboutAOUnit/utils.js b/src/components/AboutAOUnit/utils.js
index eb0295cf6..88bae014c 100644
--- a/src/components/AboutAOUnit/utils.js
+++ b/src/components/AboutAOUnit/utils.js
@@ -3,6 +3,8 @@ import i18n from '@dhis2/d2-i18n'
export const AO_TYPE_VISUALIZATION = 'visualization'
export const AO_TYPE_MAP = 'map'
export const AO_TYPE_EVENT_VISUALIZATION = 'eventVisualization'
+export const AO_TYPE_EVENT_CHART = 'eventChart'
+export const AO_TYPE_EVENT_REPORT = 'eventReport'
export const AOTypeMap = {
[AO_TYPE_VISUALIZATION]: {
@@ -14,6 +16,12 @@ export const AOTypeMap = {
[AO_TYPE_EVENT_VISUALIZATION]: {
apiEndpoint: 'eventVisualizations',
},
+ [AO_TYPE_EVENT_CHART]: {
+ apiEndpoint: 'eventCharts',
+ },
+ [AO_TYPE_EVENT_REPORT]: {
+ apiEndpoint: 'eventReports',
+ },
}
const NO_TYPE = 'NO_TYPE'
@@ -28,6 +36,12 @@ const texts = {
[AO_TYPE_VISUALIZATION]: {
unitTitle: i18n.t('About this visualization'),
},
+ [AO_TYPE_EVENT_CHART]: {
+ unitTitle: i18n.t('About this event chart'),
+ },
+ [AO_TYPE_EVENT_REPORT]: {
+ unitTitle: i18n.t('About this event report'),
+ },
[NO_TYPE]: {
unitTitle: i18n.t('About this visualization'),
},
From e347564d4c18d4f9d026f1a312ec44a538246eca Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Tue, 27 Aug 2024 11:48:25 +0000
Subject: [PATCH 107/130] chore(release): cut 26.8.2 [skip ci]
## [26.8.2](https://github.com/dhis2/analytics/compare/v26.8.1...v26.8.2) (2024-08-27)
### Bug Fixes
* add AO TYPE for event chart and event report ([#1697](https://github.com/dhis2/analytics/issues/1697)) ([efff1c8](https://github.com/dhis2/analytics/commit/efff1c81845a974fe8c60b593e6bbe42c19682d7))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 3d56447e4..bdc7663da 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.8.2](https://github.com/dhis2/analytics/compare/v26.8.1...v26.8.2) (2024-08-27)
+
+
+### Bug Fixes
+
+* add AO TYPE for event chart and event report ([#1697](https://github.com/dhis2/analytics/issues/1697)) ([efff1c8](https://github.com/dhis2/analytics/commit/efff1c81845a974fe8c60b593e6bbe42c19682d7))
+
## [26.8.1](https://github.com/dhis2/analytics/compare/v26.8.0...v26.8.1) (2024-08-08)
diff --git a/package.json b/package.json
index ab86e2261..dcbaffe99 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.8.1",
+ "version": "26.8.2",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 3392d783b51dd8715beb09b673e567580005a0a2 Mon Sep 17 00:00:00 2001
From: Edoardo Sabadelli
Date: Tue, 27 Aug 2024 15:12:31 +0200
Subject: [PATCH 108/130] fix: compute subtotals/totals for boolean types
(DHIS2-9155) (#1696)
Use 2 decimals as default
This is to align with the recent change in the backend where values are
returned with 2 decimals by default.
---
src/modules/__tests__/renderValue.spec.js | 20 ++++++++++----------
src/modules/pivotTable/PivotTableEngine.js | 17 +++++++++++++++--
src/modules/renderValue.js | 2 +-
3 files changed, 26 insertions(+), 13 deletions(-)
diff --git a/src/modules/__tests__/renderValue.spec.js b/src/modules/__tests__/renderValue.spec.js
index 845629bbe..eaf3d2a7c 100644
--- a/src/modules/__tests__/renderValue.spec.js
+++ b/src/modules/__tests__/renderValue.spec.js
@@ -25,21 +25,21 @@ const tests = [
// Numbers
{
value: 1000.5,
- expected: '1 000.5',
+ expected: '1 000.50',
valueType: VALUE_TYPE_NUMBER,
round: true,
dgs: DGS_SPACE,
},
{
- value: 33777889.55,
- expected: '33,777,889.5',
+ value: 33777889.555,
+ expected: '33,777,889.55',
valueType: VALUE_TYPE_NUMBER,
round: true,
dgs: DGS_COMMA,
},
{
value: 33777889.556,
- expected: '33 777 889.6',
+ expected: '33 777 889.56',
valueType: VALUE_TYPE_NUMBER,
round: true,
dgs: DGS_SPACE,
@@ -53,7 +53,7 @@ const tests = [
},
{
value: 33777889.56,
- expected: '33777889.6',
+ expected: '33777889.56',
valueType: VALUE_TYPE_NUMBER,
round: true,
dgs: DGS_NONE,
@@ -74,7 +74,7 @@ const tests = [
},
{
value: 1.101,
- expected: '1.1',
+ expected: '1.10',
valueType: VALUE_TYPE_NUMBER,
round: true,
dgs: DGS_SPACE,
@@ -135,16 +135,16 @@ const tests = [
dgs: DGS_SPACE,
},
{
- value: -0.0234,
- expected: '-2.3%',
+ value: -0.02345,
+ expected: '-2.34%',
valueType: VALUE_TYPE_NUMBER,
numberType: NUMBER_TYPE_ROW_PERCENTAGE,
round: true,
dgs: DGS_SPACE,
},
{
- value: -0.0234,
- expected: '-2.34%',
+ value: -0.02345,
+ expected: '-2.345%',
valueType: VALUE_TYPE_NUMBER,
numberType: NUMBER_TYPE_ROW_PERCENTAGE,
round: false,
diff --git a/src/modules/pivotTable/PivotTableEngine.js b/src/modules/pivotTable/PivotTableEngine.js
index 7b90e0935..6d16a8985 100644
--- a/src/modules/pivotTable/PivotTableEngine.js
+++ b/src/modules/pivotTable/PivotTableEngine.js
@@ -8,7 +8,12 @@ import {
} from '../dataTypes.js'
import { DIMENSION_ID_ORGUNIT } from '../predefinedDimensions.js'
import { renderValue } from '../renderValue.js'
-import { VALUE_TYPE_NUMBER, VALUE_TYPE_TEXT } from '../valueTypes.js'
+import {
+ VALUE_TYPE_NUMBER,
+ VALUE_TYPE_TEXT,
+ isBooleanValueType,
+ isNumericValueType,
+} from '../valueTypes.js'
import { AdaptiveClippingController } from './AdaptiveClippingController.js'
import { addToTotalIfNumber } from './addToTotalIfNumber.js'
import { parseValue } from './parseValue.js'
@@ -744,7 +749,15 @@ export class PivotTableEngine {
totalCell.valueType = currentValueType
}
- if (dxDimension?.valueType === VALUE_TYPE_NUMBER) {
+ // compute subtotals and totals for all numeric and boolean value types
+ // in that case, force value type of subtotal and total cells to NUMBER to format them correctly
+ // (see DHIS2-9155)
+ if (
+ isNumericValueType(dxDimension?.valueType) ||
+ isBooleanValueType(dxDimension?.valueType)
+ ) {
+ totalCell.valueType = VALUE_TYPE_NUMBER
+
dataFields.forEach((field) => {
const headerIndex = this.dimensionLookup.dataHeaders[field]
const value = parseValue(dataRow[headerIndex])
diff --git a/src/modules/renderValue.js b/src/modules/renderValue.js
index 5e87629f1..9c2f1c763 100644
--- a/src/modules/renderValue.js
+++ b/src/modules/renderValue.js
@@ -47,7 +47,7 @@ const toFixedPrecisionString = (value, skipRounding) => {
return value
}
- const precision = skipRounding ? 10 : value > -1 && value < 1 ? 2 : 1
+ const precision = skipRounding ? 10 : 2
return value.toFixed(precision)
}
From 66cd1468bf9acfc71dac0ff360ba9716137d2f09 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Tue, 27 Aug 2024 13:17:40 +0000
Subject: [PATCH 109/130] chore(release): cut 26.8.3 [skip ci]
## [26.8.3](https://github.com/dhis2/analytics/compare/v26.8.2...v26.8.3) (2024-08-27)
### Bug Fixes
* compute subtotals/totals for boolean types (DHIS2-9155) ([#1696](https://github.com/dhis2/analytics/issues/1696)) ([3392d78](https://github.com/dhis2/analytics/commit/3392d783b51dd8715beb09b673e567580005a0a2))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index bdc7663da..3cfb413ef 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.8.3](https://github.com/dhis2/analytics/compare/v26.8.2...v26.8.3) (2024-08-27)
+
+
+### Bug Fixes
+
+* compute subtotals/totals for boolean types (DHIS2-9155) ([#1696](https://github.com/dhis2/analytics/issues/1696)) ([3392d78](https://github.com/dhis2/analytics/commit/3392d783b51dd8715beb09b673e567580005a0a2))
+
## [26.8.2](https://github.com/dhis2/analytics/compare/v26.8.1...v26.8.2) (2024-08-27)
diff --git a/package.json b/package.json
index dcbaffe99..be8d2bc83 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.8.2",
+ "version": "26.8.3",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From ae4dbe63add659b4a2d0c8aab543721b0a85ab60 Mon Sep 17 00:00:00 2001
From: Bruno Raimbault
Date: Thu, 12 Sep 2024 14:59:54 +0200
Subject: [PATCH 110/130] fix: add translucent prop to CachedDataQueryProvider
(DHIS2-18029) (#1699)
translucent is optional and defaults to same value as before: true
In CachedDataQueryProvider, the translucent prop of the Layer component
was always true caused flashing grey backgrounds when loading main maps-app
and its plugin in dashboard.
---
src/components/CachedDataQueryProvider.js | 10 ++++++++--
1 file changed, 8 insertions(+), 2 deletions(-)
diff --git a/src/components/CachedDataQueryProvider.js b/src/components/CachedDataQueryProvider.js
index 47646a1f1..e4a3786d0 100644
--- a/src/components/CachedDataQueryProvider.js
+++ b/src/components/CachedDataQueryProvider.js
@@ -6,7 +6,12 @@ import React, { createContext, useContext } from 'react'
const CachedDataQueryCtx = createContext({})
-const CachedDataQueryProvider = ({ query, dataTransformation, children }) => {
+const CachedDataQueryProvider = ({
+ query,
+ dataTransformation,
+ children,
+ translucent = true,
+}) => {
const { data: rawData, ...rest } = useDataQuery(query)
const { error, loading } = rest
const data =
@@ -14,7 +19,7 @@ const CachedDataQueryProvider = ({ query, dataTransformation, children }) => {
if (loading) {
return (
-
+
@@ -43,6 +48,7 @@ CachedDataQueryProvider.propTypes = {
children: PropTypes.node.isRequired,
query: PropTypes.object.isRequired,
dataTransformation: PropTypes.func,
+ translucent: PropTypes.bool,
}
const useCachedDataQuery = () => useContext(CachedDataQueryCtx)
From 85496833afd4e0ab32b4e0d1bddf659505c31153 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Thu, 12 Sep 2024 13:03:35 +0000
Subject: [PATCH 111/130] chore(release): cut 26.8.4 [skip ci]
## [26.8.4](https://github.com/dhis2/analytics/compare/v26.8.3...v26.8.4) (2024-09-12)
### Bug Fixes
* add translucent prop to CachedDataQueryProvider (DHIS2-18029) ([#1699](https://github.com/dhis2/analytics/issues/1699)) ([ae4dbe6](https://github.com/dhis2/analytics/commit/ae4dbe63add659b4a2d0c8aab543721b0a85ab60))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 3cfb413ef..d3486be97 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.8.4](https://github.com/dhis2/analytics/compare/v26.8.3...v26.8.4) (2024-09-12)
+
+
+### Bug Fixes
+
+* add translucent prop to CachedDataQueryProvider (DHIS2-18029) ([#1699](https://github.com/dhis2/analytics/issues/1699)) ([ae4dbe6](https://github.com/dhis2/analytics/commit/ae4dbe63add659b4a2d0c8aab543721b0a85ab60))
+
## [26.8.3](https://github.com/dhis2/analytics/compare/v26.8.2...v26.8.3) (2024-08-27)
diff --git a/package.json b/package.json
index be8d2bc83..5ff052fbc 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.8.3",
+ "version": "26.8.4",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 6285f9a43d7adf2b61bbe8bfbaae865380fb8b8a Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 22 Sep 2024 03:44:24 +0200
Subject: [PATCH 112/130] fix(translations): sync translations from transifex
(master)
Automatically merged.
---
i18n/es.po | 74 +++++++++++++++++++++++++++++-------------------------
1 file changed, 40 insertions(+), 34 deletions(-)
diff --git a/i18n/es.po b/i18n/es.po
index cfcf5b213..df5f2b426 100644
--- a/i18n/es.po
+++ b/i18n/es.po
@@ -14,7 +14,7 @@
msgid ""
msgstr ""
"Project-Id-Version: i18next-conv\n"
-"POT-Creation-Date: 2024-01-25T12:05:03.360Z\n"
+"POT-Creation-Date: 2024-08-27T11:29:09.031Z\n"
"PO-Revision-Date: 2020-04-28 22:05+0000\n"
"Last-Translator: Enzo Nicolas Rossi , 2024\n"
"Language-Team: Spanish (https://app.transifex.com/hisp-uio/teams/100509/es/)\n"
@@ -86,6 +86,12 @@ msgstr "Acerca de este listado"
msgid "About this visualization"
msgstr "Acerca de esta visualización"
+msgid "About this event chart"
+msgstr "Acerca de este gráfico de eventos"
+
+msgid "About this event report"
+msgstr "Acerca de este informe"
+
msgid "This app could not retrieve required data."
msgstr "Esta aplicación no pudo recuperar los datos requeridos."
@@ -456,39 +462,6 @@ msgstr "No se pudo actualizar la interpretación"
msgid "Enter interpretation text"
msgstr "Introducir el texto de la interpretación"
-msgid "Bold text"
-msgstr "Texto en negrita"
-
-msgid "Italic text"
-msgstr "Texto en cursiva"
-
-msgid "Link to a URL"
-msgstr "Enlace a una URL"
-
-msgid "Mention a user"
-msgstr "Mencionar a un usuario"
-
-msgid "Add emoji"
-msgstr "Añadir emoji"
-
-msgid "Preview"
-msgstr "Vista previa"
-
-msgid "Back to write mode"
-msgstr "Volver al modo de escritura"
-
-msgid "Too many results. Try refining the search."
-msgstr "Demasiados resultados. Intenta refinar la búsqueda."
-
-msgid "Search for a user"
-msgstr "Buscar un usuario"
-
-msgid "Searching for \"{{- searchText}}\""
-msgstr "Buscando \"{{- searchText}}\""
-
-msgid "No results found"
-msgstr "No results found"
-
msgid "Not available offline"
msgstr "No disponible sin conexión a internet"
@@ -916,6 +889,27 @@ msgstr "Años fiscales"
msgid "Years"
msgstr "Años"
+msgid "Bold text"
+msgstr "Texto en negrita"
+
+msgid "Italic text"
+msgstr "Texto en cursiva"
+
+msgid "Link to a URL"
+msgstr "Enlace a una URL"
+
+msgid "Mention a user"
+msgstr "Mencionar a un usuario"
+
+msgid "Add emoji"
+msgstr "Añadir emoji"
+
+msgid "Preview"
+msgstr "Vista previa"
+
+msgid "Back to write mode"
+msgstr "Volver al modo de escritura"
+
msgid "Interpretations and details"
msgstr "Interpretaciones y detalles"
@@ -946,6 +940,18 @@ msgstr "No se pudieron cargar las traducciones"
msgid "Retry"
msgstr "Reintentar"
+msgid "Too many results. Try refining the search."
+msgstr "Demasiados resultados. Intenta refinar la búsqueda."
+
+msgid "Search for a user"
+msgstr "Buscar un usuario"
+
+msgid "Searching for \"{{- searchText}}\""
+msgstr "Buscando \"{{- searchText}}\""
+
+msgid "No results found"
+msgstr "No results found"
+
msgid "Series"
msgstr "Series"
From 04c9ebf0721b6b545b35297a95e7317839f33970 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 22 Sep 2024 01:48:00 +0000
Subject: [PATCH 113/130] chore(release): cut 26.8.5 [skip ci]
## [26.8.5](https://github.com/dhis2/analytics/compare/v26.8.4...v26.8.5) (2024-09-22)
### Bug Fixes
* **translations:** sync translations from transifex (master) ([6285f9a](https://github.com/dhis2/analytics/commit/6285f9a43d7adf2b61bbe8bfbaae865380fb8b8a))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index d3486be97..e8890cb2b 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.8.5](https://github.com/dhis2/analytics/compare/v26.8.4...v26.8.5) (2024-09-22)
+
+
+### Bug Fixes
+
+* **translations:** sync translations from transifex (master) ([6285f9a](https://github.com/dhis2/analytics/commit/6285f9a43d7adf2b61bbe8bfbaae865380fb8b8a))
+
## [26.8.4](https://github.com/dhis2/analytics/compare/v26.8.3...v26.8.4) (2024-09-12)
diff --git a/package.json b/package.json
index 5ff052fbc..18ea8cc83 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.8.4",
+ "version": "26.8.5",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 60f505e792cceafba9ba8275031fad82641d9411 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 6 Oct 2024 03:44:26 +0200
Subject: [PATCH 114/130] fix(translations): sync translations from transifex
(master)
Automatically merged.
---
i18n/zh.po | 112 ++++++++++++++++++++++++++++-------------------------
1 file changed, 59 insertions(+), 53 deletions(-)
diff --git a/i18n/zh.po b/i18n/zh.po
index 529b2383d..cefd5a3e8 100644
--- a/i18n/zh.po
+++ b/i18n/zh.po
@@ -8,7 +8,7 @@
msgid ""
msgstr ""
"Project-Id-Version: i18next-conv\n"
-"POT-Creation-Date: 2024-01-25T12:05:03.360Z\n"
+"POT-Creation-Date: 2024-08-27T11:29:09.031Z\n"
"PO-Revision-Date: 2020-04-28 22:05+0000\n"
"Last-Translator: easylin , 2024\n"
"Language-Team: Chinese (https://app.transifex.com/hisp-uio/teams/100509/zh/)\n"
@@ -50,7 +50,7 @@ msgstr "已创建 {{time}}"
msgid "Viewed {{count}} times"
msgid_plural "Viewed {{count}} times"
-msgstr[0] "查看了 {{count}} 次"
+msgstr[0] "查看了 {{count}} 条"
msgid "Notifications"
msgstr "通知"
@@ -76,6 +76,12 @@ msgstr "关于此行列表"
msgid "About this visualization"
msgstr "关于此可视化"
+msgid "About this event chart"
+msgstr "关于该事件图表"
+
+msgid "About this event report"
+msgstr "关于本事件报表"
+
msgid "This app could not retrieve required data."
msgstr "此应用无法检索所需数据。"
@@ -124,7 +130,7 @@ msgid "Yes, delete"
msgstr "是的,删除"
msgid "Totals only"
-msgstr "总计"
+msgstr "仅总数"
msgid "Details only"
msgstr "仅详细信息"
@@ -429,39 +435,6 @@ msgstr "无法更新解释"
msgid "Enter interpretation text"
msgstr "输入解释文本"
-msgid "Bold text"
-msgstr "粗体文字"
-
-msgid "Italic text"
-msgstr "斜体文字"
-
-msgid "Link to a URL"
-msgstr "链接到 URL"
-
-msgid "Mention a user"
-msgstr "提及用户"
-
-msgid "Add emoji"
-msgstr "添加表情符号"
-
-msgid "Preview"
-msgstr "预览"
-
-msgid "Back to write mode"
-msgstr "返回写入模式"
-
-msgid "Too many results. Try refining the search."
-msgstr "结果太多。尝试优化搜索。"
-
-msgid "Search for a user"
-msgstr "搜索用户"
-
-msgid "Searching for \"{{- searchText}}\""
-msgstr "搜索“{{- searchText}}”"
-
-msgid "No results found"
-msgstr "没有结果"
-
msgid "Not available offline"
msgstr "离线不可用"
@@ -704,13 +677,13 @@ msgid "Financial year (Start November)"
msgstr "财政年(11月始)"
msgid "Financial year (Start October)"
-msgstr "财务十月"
+msgstr "财政年度(10 月开始)"
msgid "Financial year (Start July)"
-msgstr "财务七月"
+msgstr "财政年度(7 月开始)"
msgid "Financial year (Start April)"
-msgstr "财务四月"
+msgstr "财政年度(4 月开始)"
msgid "Today"
msgstr "今天"
@@ -746,16 +719,16 @@ msgid "Last week"
msgstr "上周"
msgid "Last 4 weeks"
-msgstr "最近四周"
+msgstr "最近 4 周"
msgid "Last 12 weeks"
-msgstr "最近12周"
+msgstr "最近 12 周"
msgid "Last 52 weeks"
-msgstr "Last 52 weeks"
+msgstr "最近52 周"
msgid "Weeks this year"
-msgstr "Weeks this year"
+msgstr "今年的周"
msgid "This bi-week"
msgstr "本双周"
@@ -776,7 +749,7 @@ msgid "Last 3 months"
msgstr "最近3个月"
msgid "Last 6 months"
-msgstr "Last 6 months"
+msgstr "最近 6 个月"
msgid "Last 12 months"
msgstr "最近12月"
@@ -788,13 +761,13 @@ msgid "This bi-month"
msgstr "本双月"
msgid "Last bi-month"
-msgstr "Last bi-month"
+msgstr "上两个月"
msgid "Last 6 bi-months"
-msgstr "Last 6 bi-months"
+msgstr "最近 6 个双月"
msgid "Bi-months this year"
-msgstr "Bi-months this year"
+msgstr "今年的双月"
msgid "This quarter"
msgstr "本季度"
@@ -803,7 +776,7 @@ msgid "Last quarter"
msgstr "最近一季"
msgid "Last 4 quarters"
-msgstr "最近四个季度"
+msgstr "最近 4 个季度"
msgid "Quarters this year"
msgstr "今年的季度"
@@ -824,7 +797,7 @@ msgid "Last financial year"
msgstr "上一财政年"
msgid "Last 5 financial years"
-msgstr "最近五个财政年"
+msgstr "最近 5 个财政年度"
msgid "This year"
msgstr "今年"
@@ -851,20 +824,41 @@ msgid "Months"
msgstr "月"
msgid "Bi-months"
-msgstr "Bi-months"
+msgstr "双月"
msgid "Quarters"
msgstr "四分之一"
msgid "Six-months"
-msgstr "Six-months"
+msgstr "六个月"
msgid "Financial Years"
-msgstr "Financial Years"
+msgstr "财政年度"
msgid "Years"
msgstr "年"
+msgid "Bold text"
+msgstr "粗体文字"
+
+msgid "Italic text"
+msgstr "斜体文字"
+
+msgid "Link to a URL"
+msgstr "链接到 URL"
+
+msgid "Mention a user"
+msgstr "提及用户"
+
+msgid "Add emoji"
+msgstr "添加表情符号"
+
+msgid "Preview"
+msgstr "预览"
+
+msgid "Back to write mode"
+msgstr "返回写入模式"
+
msgid "Interpretations and details"
msgstr "解释和细节"
@@ -895,6 +889,18 @@ msgstr "无法加载翻译"
msgid "Retry"
msgstr "重试"
+msgid "Too many results. Try refining the search."
+msgstr "结果太多。尝试优化搜索。"
+
+msgid "Search for a user"
+msgstr "搜索用户"
+
+msgid "Searching for \"{{- searchText}}\""
+msgstr "搜索“{{- searchText}}”"
+
+msgid "No results found"
+msgstr "没有结果"
+
msgid "Series"
msgstr "系列"
@@ -1154,7 +1160,7 @@ msgid "Radar"
msgstr "雷达图"
msgid "Scatter"
-msgstr "分散"
+msgstr "散点图"
msgid "Single value"
msgstr "单个值"
From b478ff0849008fb4a4ab202f585716b1e789af5e Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 6 Oct 2024 01:48:08 +0000
Subject: [PATCH 115/130] chore(release): cut 26.8.6 [skip ci]
## [26.8.6](https://github.com/dhis2/analytics/compare/v26.8.5...v26.8.6) (2024-10-06)
### Bug Fixes
* **translations:** sync translations from transifex (master) ([60f505e](https://github.com/dhis2/analytics/commit/60f505e792cceafba9ba8275031fad82641d9411))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index e8890cb2b..1b7e5aa81 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.8.6](https://github.com/dhis2/analytics/compare/v26.8.5...v26.8.6) (2024-10-06)
+
+
+### Bug Fixes
+
+* **translations:** sync translations from transifex (master) ([60f505e](https://github.com/dhis2/analytics/commit/60f505e792cceafba9ba8275031fad82641d9411))
+
## [26.8.5](https://github.com/dhis2/analytics/compare/v26.8.4...v26.8.5) (2024-09-22)
diff --git a/package.json b/package.json
index 18ea8cc83..49ad4513a 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.8.5",
+ "version": "26.8.6",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From a2bfd203cb53f174106d8b570cea52cbfc6136f7 Mon Sep 17 00:00:00 2001
From: Edoardo Sabadelli
Date: Fri, 18 Oct 2024 11:43:15 +0200
Subject: [PATCH 116/130] fix: compute totals and cumulative values for
numeric/boolean types respecting totalAggregationType (DHIS2-9155) (#1700)
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
* fix: accumulate numeric (not PERCENTAGE, UNIT_INTERVAL) and boolean values
This makes the cumulative values feature more in line with the way
totals are computed.
The difference is that there is no accumulation for PERCENTAGE and
UNIT_INTERVAL types as these don't accumulate with a simple sum.
* fix: allow totals for all numeric/boolean, respect totalAggregationType
For row totals where 1 or more columns have a non-numeric/boolean data element, N/A is returned for the total cell.
For column totals, the totalAggregationType of the data element is used to compute
the total value.
* fix: style N/A differently than a normal value
* feat: allow custom title for cells
Normally the title is the same as the cell's content.
When cumulative values are used it help to see the original value in the
title and the accumulated value in the cell.
It's also useful to give some more info about a particular value (ie.
N/A).
* fix: avoid to show 0 for non cumulative types when cumulative is enabled
* refactor: replace ||= operator, not transformed by Babel
* fix: fix regression for DHIS2-17297
* fix: always use "Value:" prefix in cell tooltip
* fix: handle better mixed values when accumulating
* fix: do not fill the table with N/A with cumulative values
Simply render the original value for non cumulative types.
The tooltip can be used when in doubt to know if a cell value is
accumulated.
* fix: only accumulate when total agg type is SUM
---------
Co-authored-by: Jan Henrik Øverland
---
i18n/en.pot | 10 +-
package.json | 1 -
.../PivotTable/PivotTableValueCell.js | 9 +-
.../PivotTable/styles/PivotTable.style.js | 5 +
src/modules/pivotTable/PivotTableEngine.js | 127 ++++++++++++++----
src/modules/pivotTable/pivotTableConstants.js | 4 +
src/modules/valueTypes.js | 11 ++
7 files changed, 134 insertions(+), 33 deletions(-)
diff --git a/i18n/en.pot b/i18n/en.pot
index 2e98715e2..8f0bb1884 100644
--- a/i18n/en.pot
+++ b/i18n/en.pot
@@ -5,8 +5,8 @@ msgstr ""
"Content-Type: text/plain; charset=utf-8\n"
"Content-Transfer-Encoding: 8bit\n"
"Plural-Forms: nplurals=2; plural=(n != 1)\n"
-"POT-Creation-Date: 2024-08-27T11:29:09.031Z\n"
-"PO-Revision-Date: 2024-08-27T11:29:09.033Z\n"
+"POT-Creation-Date: 2024-10-11T12:49:26.846Z\n"
+"PO-Revision-Date: 2024-10-11T12:49:26.847Z\n"
msgid "view only"
msgstr "view only"
@@ -855,6 +855,9 @@ msgstr "Financial Years"
msgid "Years"
msgstr "Years"
+msgid "Value: {{value}}"
+msgstr "Value: {{value}}"
+
msgid "Bold text"
msgstr "Bold text"
@@ -1125,6 +1128,9 @@ msgstr "{{thresholdFactor}} × Z-score low"
msgid "{{thresholdFactor}} × Z-score high"
msgstr "{{thresholdFactor}} × Z-score high"
+msgid "Not applicable"
+msgstr "Not applicable"
+
msgid "Data"
msgstr "Data"
diff --git a/package.json b/package.json
index 49ad4513a..2d024f2e7 100644
--- a/package.json
+++ b/package.json
@@ -20,7 +20,6 @@
},
"scripts": {
"build": "d2-app-scripts build",
- "postbuild": "yarn build-storybook",
"build-storybook": "build-storybook",
"start-storybook": "start-storybook --port 5000",
"start": "yarn start-storybook",
diff --git a/src/components/PivotTable/PivotTableValueCell.js b/src/components/PivotTable/PivotTableValueCell.js
index 78d204f2c..f20fe554d 100644
--- a/src/components/PivotTable/PivotTableValueCell.js
+++ b/src/components/PivotTable/PivotTableValueCell.js
@@ -1,3 +1,4 @@
+import i18n from '@dhis2/d2-i18n'
import PropTypes from 'prop-types'
import React, { useRef } from 'react'
import { applyLegendSet } from '../../modules/pivotTable/applyLegendSet.js'
@@ -74,7 +75,13 @@ export const PivotTableValueCell = ({
{
switch (overrideTotalAggregationType || totalAggregationType) {
case AGGREGATE_TYPE_NA:
- return 'N/A'
+ return VALUE_NA
case AGGREGATE_TYPE_AVERAGE:
return (
((numerator || value) * multiplier) /
@@ -401,19 +404,46 @@ export class PivotTableEngine {
rawCell.renderedValue = renderedValue
}
+ if (
+ [CELL_TYPE_TOTAL, CELL_TYPE_SUBTOTAL].includes(rawCell.cellType) &&
+ rawCell.rawValue === AGGREGATE_TYPE_NA
+ ) {
+ rawCell.titleValue = i18n.t('Not applicable')
+ }
+
if (this.options.cumulativeValues) {
+ let titleValue
+
+ if (this.data[row] && this.data[row][column]) {
+ const dataRow = this.data[row][column]
+
+ const rawValue =
+ cellType === CELL_TYPE_VALUE
+ ? dataRow[this.dimensionLookup.dataHeaders.value]
+ : dataRow.value
+
+ titleValue = i18n.t('Value: {{value}}', {
+ value: renderValue(rawValue, valueType, this.visualization),
+ nsSeparator: '^^',
+ })
+ }
+
const cumulativeValue = this.getCumulative({
row,
column,
})
if (cumulativeValue !== undefined && cumulativeValue !== null) {
- // force to NUMBER for accumulated values
+ // force to TEXT for N/A (accumulated) values
+ // force to NUMBER for accumulated values if no valueType present
rawCell.valueType =
- valueType === undefined || valueType === null
+ cumulativeValue === VALUE_NA
+ ? VALUE_TYPE_NA
+ : valueType === undefined || valueType === null
? VALUE_TYPE_NUMBER
: valueType
rawCell.empty = false
+ rawCell.titleValue = titleValue
rawCell.rawValue = cumulativeValue
rawCell.renderedValue = renderValue(
cumulativeValue,
@@ -523,16 +553,12 @@ export class PivotTableEngine {
const cellValue = this.data[row][column]
+ // empty cell
if (!cellValue) {
- // Empty cell
- // The cell still needs to get the valueType to render correctly 0 and cumulative values
- return {
- valueType: VALUE_TYPE_NUMBER,
- totalAggregationType: AGGREGATE_TYPE_SUM,
- }
+ return undefined
}
- if (!Array.isArray(cellValue)) {
+ if (cellValue && !Array.isArray(cellValue)) {
// This is a total cell
return {
valueType: cellValue.valueType,
@@ -741,23 +767,30 @@ export class PivotTableEngine {
totalCell.totalAggregationType = currentAggType
}
- const currentValueType = dxDimension?.valueType
+ // Force value type of total cells to NUMBER for value cells with numeric or boolean types.
+ // This is to simplify the code below where we compare the previous value type.
+ // All numeric/boolean value types use the same style for rendering the total cell (right aligned content)
+ // and using NUMBER for the total cell is enough for that.
+ // (see DHIS2-9155)
+ const currentValueType =
+ isNumericValueType(dxDimension?.valueType) ||
+ isBooleanValueType(dxDimension?.valueType)
+ ? VALUE_TYPE_NUMBER
+ : dxDimension?.valueType
+
const previousValueType = totalCell.valueType
if (previousValueType && currentValueType !== previousValueType) {
- totalCell.valueType = AGGREGATE_TYPE_NA
+ totalCell.valueType = VALUE_TYPE_NA
} else {
totalCell.valueType = currentValueType
}
- // compute subtotals and totals for all numeric and boolean value types
- // in that case, force value type of subtotal and total cells to NUMBER to format them correctly
+ // Compute totals for all numeric and boolean value types only.
+ // In practice valueType here is NUMBER (see the comment above).
+ // When is not, it means there is some value cell with a valueType other than numeric/boolean,
+ // the total should not be computed then.
// (see DHIS2-9155)
- if (
- isNumericValueType(dxDimension?.valueType) ||
- isBooleanValueType(dxDimension?.valueType)
- ) {
- totalCell.valueType = VALUE_TYPE_NUMBER
-
+ if (isNumericValueType(totalCell.valueType)) {
dataFields.forEach((field) => {
const headerIndex = this.dimensionLookup.dataHeaders[field]
const value = parseValue(dataRow[headerIndex])
@@ -882,6 +915,28 @@ export class PivotTableEngine {
}
}
}
+
+ computeOverrideTotalAggregationType(totalCell, visualization) {
+ // Avoid undefined on total cells with valueTypes that cannot be totalized.
+ // This happens for example when a column/row has all value cells of type TEXT.
+ if (
+ !(
+ isNumericValueType(totalCell.valueType) ||
+ isBooleanValueType(totalCell.valueType)
+ )
+ ) {
+ return AGGREGATE_TYPE_NA
+ }
+
+ // DHIS2-15698: do not override total aggregation type when numberType option is not present
+ // (numberType option default is VALUE)
+ return (
+ visualization.numberType &&
+ visualization.numberType !== NUMBER_TYPE_VALUE &&
+ AGGREGATE_TYPE_SUM
+ )
+ }
+
finalizeTotal({ row, column }) {
if (!this.data[row]) {
return
@@ -890,12 +945,17 @@ export class PivotTableEngine {
if (totalCell && totalCell.count) {
totalCell.value = applyTotalAggregationType(
totalCell,
- // DHIS2-15698: do not override total aggregation type when numberType option is not present
- // (numberType option default is VALUE)
- this.visualization.numberType &&
- this.visualization.numberType !== NUMBER_TYPE_VALUE &&
- AGGREGATE_TYPE_SUM
+ this.computeOverrideTotalAggregationType(
+ totalCell,
+ this.visualization
+ )
)
+
+ // override valueType for styling cells with N/A value
+ if (totalCell.value === AGGREGATE_TYPE_NA) {
+ totalCell.valueType = VALUE_TYPE_NA
+ }
+
this.adaptiveClippingController.add(
{ row, column },
renderValue(
@@ -1028,10 +1088,19 @@ export class PivotTableEngine {
column,
})
const valueType = dxDimension?.valueType || VALUE_TYPE_TEXT
+ const totalAggregationType =
+ dxDimension?.totalAggregationType
+
+ // only accumulate numeric (except for PERCENTAGE and UNIT_INTERVAL) and boolean values
+ // accumulating other value types like text values does not make sense
+ if (
+ isCumulativeValueType(valueType) &&
+ totalAggregationType === AGGREGATE_TYPE_SUM
+ ) {
+ // initialise to 0 for cumulative types
+ // (||= is not transformed correctly in Babel with the current setup)
+ acc || (acc = 0)
- // only accumulate numeric values
- // accumulating text values does not make sense
- if (valueType === VALUE_TYPE_NUMBER) {
if (this.data[row] && this.data[row][column]) {
const dataRow = this.data[row][column]
@@ -1049,7 +1118,7 @@ export class PivotTableEngine {
}
return acc
- }, 0)
+ }, '')
})
} else {
this.accumulators = { rows: {} }
diff --git a/src/modules/pivotTable/pivotTableConstants.js b/src/modules/pivotTable/pivotTableConstants.js
index 1221972c9..1ab1b290d 100644
--- a/src/modules/pivotTable/pivotTableConstants.js
+++ b/src/modules/pivotTable/pivotTableConstants.js
@@ -9,6 +9,8 @@ export const AGGREGATE_TYPE_SUM = 'SUM'
export const AGGREGATE_TYPE_AVERAGE = 'AVERAGE'
export const AGGREGATE_TYPE_NA = 'N/A'
+export const VALUE_TYPE_NA = 'N_A' // this ends up as CSS class and / is problematic
+
export const NUMBER_TYPE_VALUE = 'VALUE'
export const NUMBER_TYPE_ROW_PERCENTAGE = 'ROW_PERCENTAGE'
export const NUMBER_TYPE_COLUMN_PERCENTAGE = 'COLUMN_PERCENTAGE'
@@ -35,3 +37,5 @@ export const WRAPPED_TEXT_JUSTIFY_BUFFER = 25
export const WRAPPED_TEXT_LINE_HEIGHT = 1.0
export const CLIPPED_AXIS_PARTITION_SIZE_PX = 1000
+
+export const VALUE_NA = 'N/A'
diff --git a/src/modules/valueTypes.js b/src/modules/valueTypes.js
index 89462b5c6..1097ac84f 100644
--- a/src/modules/valueTypes.js
+++ b/src/modules/valueTypes.js
@@ -36,5 +36,16 @@ const NUMERIC_VALUE_TYPES = [
const BOOLEAN_VALUE_TYPES = [VALUE_TYPE_BOOLEAN, VALUE_TYPE_TRUE_ONLY]
+const CUMULATIVE_VALUE_TYPES = [
+ VALUE_TYPE_NUMBER,
+ VALUE_TYPE_INTEGER,
+ VALUE_TYPE_INTEGER_POSITIVE,
+ VALUE_TYPE_INTEGER_NEGATIVE,
+ VALUE_TYPE_INTEGER_ZERO_OR_POSITIVE,
+ ...BOOLEAN_VALUE_TYPES,
+]
+
+export const isCumulativeValueType = (type) =>
+ CUMULATIVE_VALUE_TYPES.includes(type)
export const isNumericValueType = (type) => NUMERIC_VALUE_TYPES.includes(type)
export const isBooleanValueType = (type) => BOOLEAN_VALUE_TYPES.includes(type)
From 786aeb4c5b65958ce05305db86b4205849e3b84f Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Fri, 18 Oct 2024 09:46:05 +0000
Subject: [PATCH 117/130] chore(release): cut 26.8.7 [skip ci]
## [26.8.7](https://github.com/dhis2/analytics/compare/v26.8.6...v26.8.7) (2024-10-18)
### Bug Fixes
* compute totals and cumulative values for numeric/boolean types respecting totalAggregationType (DHIS2-9155) ([#1700](https://github.com/dhis2/analytics/issues/1700)) ([a2bfd20](https://github.com/dhis2/analytics/commit/a2bfd203cb53f174106d8b570cea52cbfc6136f7))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 1b7e5aa81..5119b6d8e 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.8.7](https://github.com/dhis2/analytics/compare/v26.8.6...v26.8.7) (2024-10-18)
+
+
+### Bug Fixes
+
+* compute totals and cumulative values for numeric/boolean types respecting totalAggregationType (DHIS2-9155) ([#1700](https://github.com/dhis2/analytics/issues/1700)) ([a2bfd20](https://github.com/dhis2/analytics/commit/a2bfd203cb53f174106d8b570cea52cbfc6136f7))
+
## [26.8.6](https://github.com/dhis2/analytics/compare/v26.8.5...v26.8.6) (2024-10-06)
diff --git a/package.json b/package.json
index 2d024f2e7..3497753b2 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.8.6",
+ "version": "26.8.7",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From f1870928b37733395d7f911f48ea7268fed97be1 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 20 Oct 2024 03:44:35 +0200
Subject: [PATCH 118/130] fix(translations): sync translations from transifex
(master)
Automatically merged.
---
i18n/lo.po | 86 +++++++++++++++++++++++++++++++-----------------------
1 file changed, 49 insertions(+), 37 deletions(-)
diff --git a/i18n/lo.po b/i18n/lo.po
index 670a341a4..d77d79e5a 100644
--- a/i18n/lo.po
+++ b/i18n/lo.po
@@ -4,15 +4,15 @@
# Somkhit Bouavong , 2022
# Philip Larsen Donnelly, 2023
# Phouthasinh PHEUAYSITHIPHONE, 2023
-# Saysamone Sibounma, 2023
# Namwan Chanthavisouk, 2024
+# Saysamone Sibounma, 2024
#
msgid ""
msgstr ""
"Project-Id-Version: i18next-conv\n"
-"POT-Creation-Date: 2024-01-25T12:05:03.360Z\n"
+"POT-Creation-Date: 2024-10-11T12:49:26.846Z\n"
"PO-Revision-Date: 2020-04-28 22:05+0000\n"
-"Last-Translator: Namwan Chanthavisouk, 2024\n"
+"Last-Translator: Saysamone Sibounma, 2024\n"
"Language-Team: Lao (https://app.transifex.com/hisp-uio/teams/100509/lo/)\n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
@@ -78,6 +78,12 @@ msgstr "ກ່ຽວກັບບັນຊີລາຍຊື່"
msgid "About this visualization"
msgstr "ກ່ຽວກັບການສ້າງພາບຂໍ້ມູນ"
+msgid "About this event chart"
+msgstr "ກ່ຽວກັບເຫດການແຜນຜັງ"
+
+msgid "About this event report"
+msgstr "ກ່ຽວກັບບົດລາຍງານເຫດການຕ່າງໆ"
+
msgid "This app could not retrieve required data."
msgstr "ແອັບນີ້ບໍ່ສາມາດດຶງຂໍ້ມູນທີ່ຕ້ອງການໄດ້"
@@ -91,7 +97,7 @@ msgid "Data / New calculation"
msgstr "ຂໍ້ມູນ / ຄິດໄລ່ໃໝ່"
msgid "Remove item"
-msgstr "ລົບລາຍການ"
+msgstr "ເອົາລາຍການອອກ"
msgid "Check formula"
msgstr "ກວດເບິ່ງສູດ"
@@ -435,39 +441,6 @@ msgstr "ບໍ່ສາມາດອັບເດດຂໍ້ຄວາມ"
msgid "Enter interpretation text"
msgstr "ປ້ອນຂໍ້ຄວາມ"
-msgid "Bold text"
-msgstr "ຕົວອັກສອນເຂັ້ມ"
-
-msgid "Italic text"
-msgstr "ຕົວອັກສອນສະຫຼ່ຽງ"
-
-msgid "Link to a URL"
-msgstr "ເຊື່ອມຕໍ່ກັບ URL"
-
-msgid "Mention a user"
-msgstr "ກ່າວເຖິງຜູ້ໃຊ້"
-
-msgid "Add emoji"
-msgstr "ເພີ່ມ emoji"
-
-msgid "Preview"
-msgstr "ເບິ່ງຕົວຢ່າງ"
-
-msgid "Back to write mode"
-msgstr "ກັບໄປທີ່ໂໝດຂຽນ"
-
-msgid "Too many results. Try refining the search."
-msgstr "ຜົນໄດ້ຮັບຫຼາຍເກີນໄປ. ປັບປຸງການຄົ້ນຫາ."
-
-msgid "Search for a user"
-msgstr "ຄົ້ນຫາຜູ້ໃຊ້"
-
-msgid "Searching for \"{{- searchText}}\""
-msgstr "ຄົ້ນຫາ \"{{- searchText}}\""
-
-msgid "No results found"
-msgstr "ບໍ່ພົບຜົນການຊອກຫາ"
-
msgid "Not available offline"
msgstr "ບໍ່ສາມາດໃຊ້ໄດ້ອອບລາຍ"
@@ -880,6 +853,30 @@ msgstr "ສົກປີງົບປະມານ"
msgid "Years"
msgstr "ປີ"
+msgid "Value: {{value}}"
+msgstr ""
+
+msgid "Bold text"
+msgstr "ຕົວອັກສອນເຂັ້ມ"
+
+msgid "Italic text"
+msgstr "ຕົວອັກສອນສະຫຼ່ຽງ"
+
+msgid "Link to a URL"
+msgstr "ເຊື່ອມຕໍ່ກັບ URL"
+
+msgid "Mention a user"
+msgstr "ກ່າວເຖິງຜູ້ໃຊ້"
+
+msgid "Add emoji"
+msgstr "ເພີ່ມ emoji"
+
+msgid "Preview"
+msgstr "ເບິ່ງຕົວຢ່າງ"
+
+msgid "Back to write mode"
+msgstr "ກັບໄປທີ່ໂໝດຂຽນ"
+
msgid "Interpretations and details"
msgstr "ຂໍ້ມູນ ແລະ ລາຍລະອຽດ"
@@ -910,6 +907,18 @@ msgstr "ບໍ່ສາມາດໂຫຼດການແປ"
msgid "Retry"
msgstr "ລອງໃໝ່"
+msgid "Too many results. Try refining the search."
+msgstr "ຜົນໄດ້ຮັບຫຼາຍເກີນໄປ. ປັບປຸງການຄົ້ນຫາ."
+
+msgid "Search for a user"
+msgstr "ຄົ້ນຫາຜູ້ໃຊ້"
+
+msgid "Searching for \"{{- searchText}}\""
+msgstr "ຄົ້ນຫາ \"{{- searchText}}\""
+
+msgid "No results found"
+msgstr "ບໍ່ພົບຜົນການຊອກຫາ"
+
msgid "Series"
msgstr "ແທ່ງ"
@@ -1117,6 +1126,9 @@ msgstr "{{thresholdFactor}} x ຄະແນນ z ຕ່ຳ"
msgid "{{thresholdFactor}} × Z-score high"
msgstr "{{thresholdFactor}} x ຄະແນນ z ສູງ"
+msgid "Not applicable"
+msgstr ""
+
msgid "Data"
msgstr "ຂໍ້ມູນ"
From 24e9ffdea7336a7b96005c3b4a67d9c25ca64b56 Mon Sep 17 00:00:00 2001
From: "@dhis2-bot"
Date: Sun, 20 Oct 2024 01:47:31 +0000
Subject: [PATCH 119/130] chore(release): cut 26.8.8 [skip ci]
## [26.8.8](https://github.com/dhis2/analytics/compare/v26.8.7...v26.8.8) (2024-10-20)
### Bug Fixes
* **translations:** sync translations from transifex (master) ([f187092](https://github.com/dhis2/analytics/commit/f1870928b37733395d7f911f48ea7268fed97be1))
---
CHANGELOG.md | 7 +++++++
package.json | 2 +-
2 files changed, 8 insertions(+), 1 deletion(-)
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 5119b6d8e..e49acbdce 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -1,3 +1,10 @@
+## [26.8.8](https://github.com/dhis2/analytics/compare/v26.8.7...v26.8.8) (2024-10-20)
+
+
+### Bug Fixes
+
+* **translations:** sync translations from transifex (master) ([f187092](https://github.com/dhis2/analytics/commit/f1870928b37733395d7f911f48ea7268fed97be1))
+
## [26.8.7](https://github.com/dhis2/analytics/compare/v26.8.6...v26.8.7) (2024-10-18)
diff --git a/package.json b/package.json
index 3497753b2..40db741ba 100644
--- a/package.json
+++ b/package.json
@@ -1,6 +1,6 @@
{
"name": "@dhis2/analytics",
- "version": "26.8.7",
+ "version": "26.8.8",
"main": "./build/cjs/index.js",
"module": "./build/es/index.js",
"exports": {
From 40fdfba1c3041cb7cf57845aa101c8a64f0cd919 Mon Sep 17 00:00:00 2001
From: Hendrik de Graaf
Date: Tue, 22 Oct 2024 16:44:51 +0200
Subject: [PATCH 120/130] feat: implement Single Value as a Highcharts.Chart
instance and add offline exporting module (#1698)
* feat: add offline exporting module
* feat: add bugfix plugins to Highcharts that address PDF export issues
* feat: implement Single Value as a Highcharts.Chart instance so it can be exported client-side
---
.storybook/preview-head.html | 6 +
src/__demo__/SingleValue.stories.js | 802 ++++++++++++++++++
.../config/adapters/dhis_dhis/index.js | 38 -
.../subtitle/__tests__/index.spec.js | 53 --
.../subtitle/__tests__/singleValue.spec.js | 15 -
.../adapters/dhis_dhis/subtitle/index.js | 33 -
.../dhis_dhis/subtitle/singleValue.js | 5 -
.../dhis_dhis/title/__tests__/index.spec.js | 36 -
.../title/__tests__/singleValue.spec.js | 21 -
.../config/adapters/dhis_dhis/title/index.js | 30 -
.../config/adapters/dhis_dhis/type.js | 10 -
.../adapters/dhis_highcharts/chart/default.js | 27 +
.../adapters/dhis_highcharts/chart/index.js | 12 +
.../dhis_highcharts/chart/singleValue.js | 19 +
.../dhis_highcharts/customSVGOptions/index.js | 29 +
.../getSingleValueBackgroundColor.js | 17 +
.../getSingleValueFormattedValue.js} | 9 +-
.../singleValue/getSingleValueLegendColor.js | 8 +
.../singleValue/getSingleValueSubtext.js | 11 +
.../singleValue/getSingleValueTextColor.js | 27 +
.../singleValue/getSingleValueTitleColor.js | 34 +
.../customSVGOptions/singleValue/index.js | 27 +
.../{chart.js => events/index.js} | 30 +-
.../events/loadCustomSVG/index.js | 12 +
.../singleValue/addIconElement.js | 32 +
.../singleValue/checkIfFitsWithinContainer.js | 29 +
.../singleValue/computeLayoutRect.js | 43 +
.../singleValue/computeSpacingTop.js | 15 +
.../loadCustomSVG/singleValue/constants.js | 4 +
.../singleValue/getAvailableSpace.js | 10 +
.../events/loadCustomSVG/singleValue/index.js | 55 ++
.../singleValue/positionElements.js | 62 ++
.../loadCustomSVG/singleValue/styles.js | 62 ++
.../adapters/dhis_highcharts/exporting.js | 25 +
.../config/adapters/dhis_highcharts/index.js | 42 +-
.../config/adapters/dhis_highcharts/lang.js | 15 +
.../adapters/dhis_highcharts/plotOptions.js | 2 +-
.../adapters/dhis_highcharts/series/index.js | 6 +-
.../subtitle/__tests__/singleValue.spec.js | 64 ++
.../dhis_highcharts/subtitle/index.js | 122 ++-
.../dhis_highcharts/subtitle/singleValue.js | 18 +
.../title/__tests__/singleValue.spec.js | 57 ++
.../adapters/dhis_highcharts/title/index.js | 114 ++-
.../title/singleValue.js | 12 +-
.../config/adapters/dhis_highcharts/type.js | 3 +
.../adapters/dhis_highcharts/xAxis/index.js | 2 +
.../adapters/dhis_highcharts/yAxis/index.js | 11 +-
src/visualizations/config/adapters/index.js | 2 -
.../config/generators/dhis/index.js | 36 -
.../config/generators/dhis/singleValue.js | 531 ------------
.../config/generators/highcharts/index.js | 9 +-
.../highcharts/pdfExportBugFixPlugin/index.js | 7 +
.../pdfExportBugFixPlugin/nonASCIIFont.js | 9 +
.../pdfExportBugFixPlugin/textShadow.js | 308 +++++++
src/visualizations/config/generators/index.js | 2 -
.../store/adapters/dhis_dhis/index.js | 102 ---
.../store/adapters/dhis_dhis/singleValue.js | 5 -
.../store/adapters/dhis_highcharts/index.js | 4 +
.../adapters/dhis_highcharts/singleValue.js | 9 +
src/visualizations/store/adapters/index.js | 2 -
.../util/shouldUseContrastColor.js | 17 +
61 files changed, 2104 insertions(+), 1055 deletions(-)
create mode 100644 .storybook/preview-head.html
create mode 100644 src/__demo__/SingleValue.stories.js
delete mode 100644 src/visualizations/config/adapters/dhis_dhis/index.js
delete mode 100644 src/visualizations/config/adapters/dhis_dhis/subtitle/__tests__/index.spec.js
delete mode 100644 src/visualizations/config/adapters/dhis_dhis/subtitle/__tests__/singleValue.spec.js
delete mode 100644 src/visualizations/config/adapters/dhis_dhis/subtitle/index.js
delete mode 100644 src/visualizations/config/adapters/dhis_dhis/subtitle/singleValue.js
delete mode 100644 src/visualizations/config/adapters/dhis_dhis/title/__tests__/index.spec.js
delete mode 100644 src/visualizations/config/adapters/dhis_dhis/title/__tests__/singleValue.spec.js
delete mode 100644 src/visualizations/config/adapters/dhis_dhis/title/index.js
delete mode 100644 src/visualizations/config/adapters/dhis_dhis/type.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/chart/default.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/chart/index.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/chart/singleValue.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/index.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueBackgroundColor.js
rename src/visualizations/config/adapters/{dhis_dhis/value/index.js => dhis_highcharts/customSVGOptions/singleValue/getSingleValueFormattedValue.js} (69%)
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueLegendColor.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueSubtext.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueTextColor.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueTitleColor.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/index.js
rename src/visualizations/config/adapters/dhis_highcharts/{chart.js => events/index.js} (51%)
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/index.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/addIconElement.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/checkIfFitsWithinContainer.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/computeLayoutRect.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/computeSpacingTop.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/constants.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/getAvailableSpace.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/index.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/positionElements.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/styles.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/exporting.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/lang.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/subtitle/__tests__/singleValue.spec.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/subtitle/singleValue.js
create mode 100644 src/visualizations/config/adapters/dhis_highcharts/title/__tests__/singleValue.spec.js
rename src/visualizations/config/adapters/{dhis_dhis => dhis_highcharts}/title/singleValue.js (50%)
delete mode 100644 src/visualizations/config/generators/dhis/index.js
delete mode 100644 src/visualizations/config/generators/dhis/singleValue.js
create mode 100644 src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/index.js
create mode 100644 src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/nonASCIIFont.js
create mode 100644 src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/textShadow.js
delete mode 100644 src/visualizations/store/adapters/dhis_dhis/index.js
delete mode 100644 src/visualizations/store/adapters/dhis_dhis/singleValue.js
create mode 100644 src/visualizations/store/adapters/dhis_highcharts/singleValue.js
create mode 100644 src/visualizations/util/shouldUseContrastColor.js
diff --git a/.storybook/preview-head.html b/.storybook/preview-head.html
new file mode 100644
index 000000000..965f8201c
--- /dev/null
+++ b/.storybook/preview-head.html
@@ -0,0 +1,6 @@
+
+
+
diff --git a/src/__demo__/SingleValue.stories.js b/src/__demo__/SingleValue.stories.js
new file mode 100644
index 000000000..c47b82cbd
--- /dev/null
+++ b/src/__demo__/SingleValue.stories.js
@@ -0,0 +1,802 @@
+import { storiesOf } from '@storybook/react'
+import React, { useState, useMemo, useRef, useEffect, useCallback } from 'react'
+import { createVisualization } from '../index.js'
+const constainerStyleBase = {
+ width: 800,
+ height: 800,
+ border: '1px solid magenta',
+ marginBottom: 14,
+}
+const innerContainerStyle = {
+ overflow: 'hidden',
+ display: 'flex',
+ justifyContent: 'center',
+ height: '100%',
+}
+
+const baseDataObj = {
+ response: {
+ headers: [
+ {
+ name: 'dx',
+ column: 'Data',
+ valueType: 'TEXT',
+ type: 'java.lang.String',
+ hidden: false,
+ meta: true,
+ },
+ {
+ name: 'value',
+ column: 'Value',
+ valueType: 'NUMBER',
+ type: 'java.lang.Double',
+ hidden: false,
+ meta: false,
+ },
+ ],
+ metaData: {
+ items: {
+ 202308: {
+ uid: '202308',
+ code: '202308',
+ name: 'August 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-08-01T00:00:00.000',
+ endDate: '2023-08-31T00:00:00.000',
+ },
+ 202309: {
+ uid: '202309',
+ code: '202309',
+ name: 'September 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-09-01T00:00:00.000',
+ endDate: '2023-09-30T00:00:00.000',
+ },
+ 202310: {
+ uid: '202310',
+ code: '202310',
+ name: 'October 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-10-01T00:00:00.000',
+ endDate: '2023-10-31T00:00:00.000',
+ },
+ 202311: {
+ uid: '202311',
+ code: '202311',
+ name: 'November 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-11-01T00:00:00.000',
+ endDate: '2023-11-30T00:00:00.000',
+ },
+ 202312: {
+ uid: '202312',
+ code: '202312',
+ name: 'December 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-12-01T00:00:00.000',
+ endDate: '2023-12-31T00:00:00.000',
+ },
+ 202401: {
+ uid: '202401',
+ code: '202401',
+ name: 'January 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-01-01T00:00:00.000',
+ endDate: '2024-01-31T00:00:00.000',
+ },
+ 202402: {
+ uid: '202402',
+ code: '202402',
+ name: 'February 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-02-01T00:00:00.000',
+ endDate: '2024-02-29T00:00:00.000',
+ },
+ 202403: {
+ uid: '202403',
+ code: '202403',
+ name: 'March 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-03-01T00:00:00.000',
+ endDate: '2024-03-31T00:00:00.000',
+ },
+ 202404: {
+ uid: '202404',
+ code: '202404',
+ name: 'April 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-04-01T00:00:00.000',
+ endDate: '2024-04-30T00:00:00.000',
+ },
+ 202405: {
+ uid: '202405',
+ code: '202405',
+ name: 'May 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-05-01T00:00:00.000',
+ endDate: '2024-05-31T00:00:00.000',
+ },
+ 202406: {
+ uid: '202406',
+ code: '202406',
+ name: 'June 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-06-01T00:00:00.000',
+ endDate: '2024-06-30T00:00:00.000',
+ },
+ 202407: {
+ uid: '202407',
+ code: '202407',
+ name: 'July 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-07-01T00:00:00.000',
+ endDate: '2024-07-31T00:00:00.000',
+ },
+ ou: {
+ uid: 'ou',
+ name: 'Organisation unit',
+ dimensionType: 'ORGANISATION_UNIT',
+ },
+ O6uvpzGd5pu: {
+ uid: 'O6uvpzGd5pu',
+ code: 'OU_264',
+ name: 'Bo',
+ dimensionItemType: 'ORGANISATION_UNIT',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ },
+ LAST_12_MONTHS: {
+ name: 'Last 12 months',
+ },
+ dx: {
+ uid: 'dx',
+ name: 'Data',
+ dimensionType: 'DATA_X',
+ },
+ pe: {
+ uid: 'pe',
+ name: 'Period',
+ dimensionType: 'PERIOD',
+ },
+ FnYCr2EAzWS: {
+ uid: 'FnYCr2EAzWS',
+ code: 'IN_52493',
+ name: 'BCG Coverage <1y',
+ legendSet: 'BtxOoQuLyg1',
+ dimensionItemType: 'INDICATOR',
+ valueType: 'NUMBER',
+ totalAggregationType: 'AVERAGE',
+ indicatorType: {
+ name: 'Per cent',
+ displayName: 'Per cent',
+ factor: 100,
+ number: false,
+ },
+ },
+ },
+ dimensions: {
+ dx: ['FnYCr2EAzWS'],
+ pe: [
+ '202308',
+ '202309',
+ '202310',
+ '202311',
+ '202312',
+ '202401',
+ '202402',
+ '202403',
+ '202404',
+ '202405',
+ '202406',
+ '202407',
+ ],
+ ou: ['O6uvpzGd5pu'],
+ co: [],
+ },
+ },
+ rowContext: {},
+ rows: [['FnYCr2EAzWS', '34.19']],
+ width: 2,
+ height: 1,
+ headerWidth: 2,
+ },
+ headers: [
+ {
+ name: 'dx',
+ column: 'Data',
+ valueType: 'TEXT',
+ type: 'java.lang.String',
+ hidden: false,
+ meta: true,
+ isPrefix: false,
+ isCollect: false,
+ index: 0,
+ },
+ {
+ name: 'value',
+ column: 'Value',
+ valueType: 'NUMBER',
+ type: 'java.lang.Double',
+ hidden: false,
+ meta: false,
+ isPrefix: false,
+ isCollect: false,
+ index: 1,
+ },
+ ],
+ rows: [['FnYCr2EAzWS', '34.19']],
+ metaData: {
+ items: {
+ 202308: {
+ uid: '202308',
+ code: '202308',
+ name: 'August 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-08-01T00:00:00.000',
+ endDate: '2023-08-31T00:00:00.000',
+ },
+ 202309: {
+ uid: '202309',
+ code: '202309',
+ name: 'September 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-09-01T00:00:00.000',
+ endDate: '2023-09-30T00:00:00.000',
+ },
+ 202310: {
+ uid: '202310',
+ code: '202310',
+ name: 'October 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-10-01T00:00:00.000',
+ endDate: '2023-10-31T00:00:00.000',
+ },
+ 202311: {
+ uid: '202311',
+ code: '202311',
+ name: 'November 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-11-01T00:00:00.000',
+ endDate: '2023-11-30T00:00:00.000',
+ },
+ 202312: {
+ uid: '202312',
+ code: '202312',
+ name: 'December 2023',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2023-12-01T00:00:00.000',
+ endDate: '2023-12-31T00:00:00.000',
+ },
+ 202401: {
+ uid: '202401',
+ code: '202401',
+ name: 'January 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-01-01T00:00:00.000',
+ endDate: '2024-01-31T00:00:00.000',
+ },
+ 202402: {
+ uid: '202402',
+ code: '202402',
+ name: 'February 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-02-01T00:00:00.000',
+ endDate: '2024-02-29T00:00:00.000',
+ },
+ 202403: {
+ uid: '202403',
+ code: '202403',
+ name: 'March 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-03-01T00:00:00.000',
+ endDate: '2024-03-31T00:00:00.000',
+ },
+ 202404: {
+ uid: '202404',
+ code: '202404',
+ name: 'April 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-04-01T00:00:00.000',
+ endDate: '2024-04-30T00:00:00.000',
+ },
+ 202405: {
+ uid: '202405',
+ code: '202405',
+ name: 'May 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-05-01T00:00:00.000',
+ endDate: '2024-05-31T00:00:00.000',
+ },
+ 202406: {
+ uid: '202406',
+ code: '202406',
+ name: 'June 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-06-01T00:00:00.000',
+ endDate: '2024-06-30T00:00:00.000',
+ },
+ 202407: {
+ uid: '202407',
+ code: '202407',
+ name: 'July 2024',
+ dimensionItemType: 'PERIOD',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ startDate: '2024-07-01T00:00:00.000',
+ endDate: '2024-07-31T00:00:00.000',
+ },
+ ou: {
+ uid: 'ou',
+ name: 'Organisation unit',
+ dimensionType: 'ORGANISATION_UNIT',
+ },
+ O6uvpzGd5pu: {
+ uid: 'O6uvpzGd5pu',
+ code: 'OU_264',
+ name: 'Bo',
+ dimensionItemType: 'ORGANISATION_UNIT',
+ valueType: 'TEXT',
+ totalAggregationType: 'SUM',
+ },
+ LAST_12_MONTHS: {
+ name: 'Last 12 months',
+ },
+ dx: {
+ uid: 'dx',
+ name: 'Data',
+ dimensionType: 'DATA_X',
+ },
+ pe: {
+ uid: 'pe',
+ name: 'Period',
+ dimensionType: 'PERIOD',
+ },
+ FnYCr2EAzWS: {
+ uid: 'FnYCr2EAzWS',
+ code: 'IN_52493',
+ name: 'BCG Coverage <1y',
+ legendSet: 'BtxOoQuLyg1',
+ dimensionItemType: 'INDICATOR',
+ valueType: 'NUMBER',
+ totalAggregationType: 'AVERAGE',
+ },
+ },
+ dimensions: {
+ dx: ['FnYCr2EAzWS'],
+ pe: [
+ '202308',
+ '202309',
+ '202310',
+ '202311',
+ '202312',
+ '202401',
+ '202402',
+ '202403',
+ '202404',
+ '202405',
+ '202406',
+ '202407',
+ ],
+ ou: ['O6uvpzGd5pu'],
+ co: [],
+ },
+ },
+}
+const numberIndicatorType = {
+ name: 'Plain',
+ number: true,
+}
+const subtextIndicatorType = {
+ name: 'Custom',
+ displayName: 'Custom subtext',
+ number: true,
+}
+const percentIndicatorType = {
+ name: 'Per cent',
+ displayName: 'Per cent',
+ factor: 100,
+ number: false,
+}
+const layout = {
+ name: 'BCG coverage last 12 months - Bo',
+ created: '2013-10-16T19:50:52.464',
+ lastUpdated: '2021-07-06T12:53:57.296',
+ translations: [],
+ favorites: [],
+ lastUpdatedBy: {
+ id: 'xE7jOejl9FI',
+ code: null,
+ name: 'John Traore',
+ displayName: 'John Traore',
+ username: 'admin',
+ },
+ regressionType: 'NONE',
+ displayDensity: 'NORMAL',
+ fontSize: 'NORMAL',
+ sortOrder: 0,
+ topLimit: 0,
+ hideEmptyRows: false,
+ showHierarchy: false,
+ completedOnly: false,
+ skipRounding: false,
+ dataDimensionItems: [
+ {
+ indicator: {
+ name: 'BCG Coverage <1y',
+ dimensionItemType: 'INDICATOR',
+ displayName: 'BCG Coverage <1y',
+ access: {
+ manage: true,
+ externalize: true,
+ write: true,
+ read: true,
+ update: true,
+ delete: true,
+ },
+ displayShortName: 'BCG Coverage <1y',
+ id: 'FnYCr2EAzWS',
+ },
+ dataDimensionItemType: 'INDICATOR',
+ },
+ ],
+ subscribers: [],
+ aggregationType: 'DEFAULT',
+ digitGroupSeparator: 'SPACE',
+ hideEmptyRowItems: 'NONE',
+ noSpaceBetweenColumns: false,
+ cumulativeValues: false,
+ percentStackedValues: false,
+ showData: true,
+ colTotals: false,
+ rowTotals: false,
+ rowSubTotals: false,
+ colSubTotals: false,
+ hideTitle: false,
+ hideSubtitle: false,
+ showDimensionLabels: false,
+ interpretations: [],
+ type: 'SINGLE_VALUE',
+ reportingParams: {
+ grandParentOrganisationUnit: false,
+ parentOrganisationUnit: false,
+ organisationUnit: false,
+ reportingPeriod: false,
+ },
+ numberType: 'VALUE',
+ fontStyle: {},
+ colorSet: 'DEFAULT',
+ yearlySeries: [],
+ regression: false,
+ hideEmptyColumns: false,
+ fixColumnHeaders: false,
+ fixRowHeaders: false,
+ filters: [
+ {
+ items: [
+ {
+ name: 'Bo',
+ dimensionItemType: 'ORGANISATION_UNIT',
+ displayShortName: 'Bo',
+ displayName: 'Bo',
+ access: {
+ manage: true,
+ externalize: true,
+ write: true,
+ read: true,
+ update: true,
+ delete: true,
+ },
+ id: 'O6uvpzGd5pu',
+ },
+ ],
+ dimension: 'ou',
+ },
+ {
+ items: [
+ {
+ name: 'LAST_12_MONTHS',
+ dimensionItemType: 'PERIOD',
+ displayShortName: 'LAST_12_MONTHS',
+ displayName: 'LAST_12_MONTHS',
+ access: {
+ manage: true,
+ externalize: true,
+ write: true,
+ read: true,
+ update: true,
+ delete: true,
+ },
+ id: 'LAST_12_MONTHS',
+ },
+ ],
+ dimension: 'pe',
+ },
+ ],
+ parentGraphMap: {
+ O6uvpzGd5pu: 'ImspTQPwCqd',
+ },
+ columns: [
+ {
+ items: [
+ {
+ name: 'BCG Coverage <1y',
+ dimensionItemType: 'INDICATOR',
+ displayName: 'BCG Coverage <1y',
+ access: {
+ manage: true,
+ externalize: true,
+ write: true,
+ read: true,
+ update: true,
+ delete: true,
+ },
+ displayShortName: 'BCG Coverage <1y',
+ id: 'FnYCr2EAzWS',
+ },
+ ],
+ dimension: 'dx',
+ },
+ ],
+ rows: [],
+ subscribed: false,
+ displayName: 'BCG coverage last 12 months - Bo',
+ access: {
+ manage: true,
+ externalize: true,
+ write: true,
+ read: true,
+ update: true,
+ delete: true,
+ },
+ favorite: false,
+ user: {
+ id: 'xE7jOejl9FI',
+ code: null,
+ name: 'John Traore',
+ displayName: 'John Traore',
+ username: 'admin',
+ },
+ href: 'http://localhost:8080/api/41/visualizations/mYMnDl5Z9oD',
+ id: 'mYMnDl5Z9oD',
+ legend: {
+ showKey: false,
+ },
+ sorting: [],
+ series: [],
+ icons: [],
+ seriesKey: {
+ hidden: false,
+ },
+ axes: [],
+}
+const icon =
+ ''
+
+const baseExtraOptions = {
+ dashboard: true,
+ animation: 200,
+ legendSets: [],
+ icon,
+}
+
+const indicatorTypes = ['plain', 'percent', 'subtext']
+
+storiesOf('SingleValue', module).add('default', () => {
+ const newChartRef = useRef(null)
+ const newContainerRef = useRef(null)
+ const [dashboard, setDashboard] = useState(false)
+ const [showIcon, setShowIcon] = useState(true)
+ const [indicatorType, setIndicatorType] = useState('plain')
+ const [exportAsPdf, setExportAsPdf] = useState(true)
+ const [width, setWidth] = useState(constainerStyleBase.width)
+ const [height, setHeight] = useState(constainerStyleBase.height)
+ const containerStyle = useMemo(
+ () => ({
+ ...constainerStyleBase,
+ width,
+ height,
+ }),
+ [width, height]
+ )
+ useEffect(() => {
+ if (newContainerRef.current) {
+ requestAnimationFrame(() => {
+ const extraOptions = {
+ ...baseExtraOptions,
+ dashboard,
+ icon: showIcon ? icon : undefined,
+ }
+ const dataObj = { ...baseDataObj }
+
+ if (indicatorType === 'plain') {
+ dataObj.metaData.items.FnYCr2EAzWS.indicatorType =
+ numberIndicatorType
+ }
+ if (indicatorType === 'percent') {
+ dataObj.metaData.items.FnYCr2EAzWS.indicatorType =
+ percentIndicatorType
+ }
+ if (indicatorType === 'subtext') {
+ dataObj.metaData.items.FnYCr2EAzWS.indicatorType =
+ subtextIndicatorType
+ }
+ const newVisualization = createVisualization(
+ [dataObj],
+ layout,
+ newContainerRef.current,
+ extraOptions,
+ undefined,
+ undefined,
+ 'highcharts'
+ )
+ newChartRef.current = newVisualization.visualization
+ })
+ }
+ }, [containerStyle, dashboard, showIcon, indicatorType])
+ const downloadOffline = useCallback(() => {
+ if (newChartRef.current) {
+ const currentBackgroundColor =
+ newChartRef.current.userOptions.chart.backgroundColor
+
+ newChartRef.current.update({
+ exporting: {
+ chartOptions: {
+ isPdfExport: exportAsPdf,
+ },
+ },
+ })
+ newChartRef.current.exportChartLocal(
+ {
+ sourceHeight: 768,
+ sourceWidth: 1024,
+ scale: 1,
+ fallbackToExportServer: false,
+ filename: 'testOfflineDownload',
+ showExportInProgress: true,
+ type: exportAsPdf ? 'application/pdf' : 'image/png',
+ },
+ {
+ chart: {
+ backgroundColor:
+ currentBackgroundColor === 'transparent'
+ ? '#ffffff'
+ : currentBackgroundColor,
+ },
+ }
+ )
+ }
+ }, [exportAsPdf])
+
+ return (
+ <>
+
+
+ >
+ )
+})
diff --git a/src/visualizations/config/adapters/dhis_dhis/index.js b/src/visualizations/config/adapters/dhis_dhis/index.js
deleted file mode 100644
index 06a5256bf..000000000
--- a/src/visualizations/config/adapters/dhis_dhis/index.js
+++ /dev/null
@@ -1,38 +0,0 @@
-import getSubtitle from './subtitle/index.js'
-import getTitle from './title/index.js'
-import getValue from './value/index.js'
-
-export const INDICATOR_FACTOR_100 = 100
-
-export default function ({ store, layout, extraOptions }) {
- const data = store.generateData({
- type: layout.type,
- seriesId:
- layout.columns && layout.columns.length
- ? layout.columns[0].dimension
- : null,
- categoryId:
- layout.rows && layout.rows.length ? layout.rows[0].dimension : null,
- })
- const metaData = store.data[0].metaData
-
- const config = {
- value: data[0],
- formattedValue:
- data[0] === undefined
- ? extraOptions.noData.text
- : getValue(data[0], layout, metaData),
- title: getTitle(layout, metaData, extraOptions.dashboard),
- subtitle: getSubtitle(layout, metaData, extraOptions.dashboard),
- }
-
- const indicatorType =
- metaData.items[metaData.dimensions.dx[0]].indicatorType
-
- // Use % symbol for factor 100 and the full string for others
- if (indicatorType?.factor !== INDICATOR_FACTOR_100) {
- config.subText = indicatorType?.displayName
- }
-
- return config
-}
diff --git a/src/visualizations/config/adapters/dhis_dhis/subtitle/__tests__/index.spec.js b/src/visualizations/config/adapters/dhis_dhis/subtitle/__tests__/index.spec.js
deleted file mode 100644
index 486333c8c..000000000
--- a/src/visualizations/config/adapters/dhis_dhis/subtitle/__tests__/index.spec.js
+++ /dev/null
@@ -1,53 +0,0 @@
-import { VIS_TYPE_SINGLE_VALUE } from '../../../../../../modules/visTypes.js'
-import getSubtitle from '../index.js'
-
-jest.mock('../singleValue', () => () => 'The sv filter title')
-jest.mock(
- '../../../../../util/getFilterText',
- () => () => 'The default filter text'
-)
-
-describe('getSubtitle', () => {
- it('returns empty subtitle when flag hideSubtitle exists', () => {
- expect(getSubtitle({ hideSubtitle: true })).toEqual('')
- })
-
- it('returns the subtitle provided in the layout', () => {
- const subtitle = 'The subtitle was already set'
- expect(getSubtitle({ subtitle })).toEqual(subtitle)
- })
-
- it('returns subtitle for single value vis', () => {
- expect(getSubtitle({ type: VIS_TYPE_SINGLE_VALUE })).toEqual(
- 'The sv filter title'
- )
- })
-
- describe('not dashboard', () => {
- describe('layout does not include title', () => {
- it('returns empty subtitle', () => {
- expect(getSubtitle({ filters: {} }, {}, false)).toEqual('')
- })
- })
-
- describe('layout includes title', () => {
- it('returns filter title as subtitle', () => {
- expect(
- getSubtitle(
- { filters: {}, title: 'Chart title' },
- {},
- false
- )
- ).toEqual('The default filter text')
- })
- })
- })
-
- describe('dashboard', () => {
- it('returns filter title as subtitle', () => {
- expect(getSubtitle({ filters: {} }, {}, true)).toEqual(
- 'The default filter text'
- )
- })
- })
-})
diff --git a/src/visualizations/config/adapters/dhis_dhis/subtitle/__tests__/singleValue.spec.js b/src/visualizations/config/adapters/dhis_dhis/subtitle/__tests__/singleValue.spec.js
deleted file mode 100644
index 39b497f64..000000000
--- a/src/visualizations/config/adapters/dhis_dhis/subtitle/__tests__/singleValue.spec.js
+++ /dev/null
@@ -1,15 +0,0 @@
-import getSingleValueSubtitle from '../singleValue.js'
-
-jest.mock('../../../../../util/getFilterText', () => () => 'The filter text')
-
-describe('getSingleValueSubtitle', () => {
- it('returns null when layout does not have filters', () => {
- expect(getSingleValueSubtitle({})).toEqual('')
- })
-
- it('returns the filter text', () => {
- expect(getSingleValueSubtitle({ filters: [] })).toEqual(
- 'The filter text'
- )
- })
-})
diff --git a/src/visualizations/config/adapters/dhis_dhis/subtitle/index.js b/src/visualizations/config/adapters/dhis_dhis/subtitle/index.js
deleted file mode 100644
index 1be507be4..000000000
--- a/src/visualizations/config/adapters/dhis_dhis/subtitle/index.js
+++ /dev/null
@@ -1,33 +0,0 @@
-import { VIS_TYPE_SINGLE_VALUE } from '../../../../../modules/visTypes.js'
-import getFilterText from '../../../../util/getFilterText.js'
-import getSingleValueTitle from './singleValue.js'
-
-function getDefault(layout, dashboard, metaData) {
- if (dashboard || typeof layout.title === 'string') {
- return getFilterText(layout.filters, metaData)
- }
-
- return ''
-}
-
-export default function (layout, metaData, dashboard) {
- if (layout.hideSubtitle) {
- return ''
- }
-
- if (typeof layout.subtitle === 'string' && layout.subtitle.length) {
- return layout.subtitle
- } else {
- let subtitle
- switch (layout.type) {
- case VIS_TYPE_SINGLE_VALUE:
- subtitle = getSingleValueTitle(layout, metaData)
-
- break
- default:
- subtitle = getDefault(layout, dashboard, metaData)
- }
-
- return subtitle
- }
-}
diff --git a/src/visualizations/config/adapters/dhis_dhis/subtitle/singleValue.js b/src/visualizations/config/adapters/dhis_dhis/subtitle/singleValue.js
deleted file mode 100644
index de246ba2f..000000000
--- a/src/visualizations/config/adapters/dhis_dhis/subtitle/singleValue.js
+++ /dev/null
@@ -1,5 +0,0 @@
-import getFilterText from '../../../../util/getFilterText.js'
-
-export default function (layout, metaData) {
- return layout.filters ? getFilterText(layout.filters, metaData) : ''
-}
diff --git a/src/visualizations/config/adapters/dhis_dhis/title/__tests__/index.spec.js b/src/visualizations/config/adapters/dhis_dhis/title/__tests__/index.spec.js
deleted file mode 100644
index 15a4b8a56..000000000
--- a/src/visualizations/config/adapters/dhis_dhis/title/__tests__/index.spec.js
+++ /dev/null
@@ -1,36 +0,0 @@
-import { VIS_TYPE_SINGLE_VALUE } from '../../../../../../modules/visTypes.js'
-import getTitle from '../index.js'
-
-jest.mock('../singleValue', () => () => 'The sv filter title')
-jest.mock('../../../../../util/getFilterText', () => () => 'The filter text')
-
-describe('getTitle', () => {
- it('returns empty title when flag hideTitle exists', () => {
- expect(getTitle({ hideTitle: true })).toEqual('')
- })
-
- it('returns the title provided in the layout', () => {
- const title = 'The title was already set'
- expect(getTitle({ title })).toEqual(title)
- })
-
- it('returns title for single value vis', () => {
- expect(getTitle({ type: VIS_TYPE_SINGLE_VALUE })).toEqual(
- 'The sv filter title'
- )
- })
-
- describe('not dashboard', () => {
- it('returns filter text as title', () => {
- expect(getTitle({ filters: {} }, {}, false)).toEqual(
- 'The filter text'
- )
- })
- })
-
- describe('dashboard', () => {
- it('returns empty string', () => {
- expect(getTitle({ filters: {} }, {}, true)).toEqual('')
- })
- })
-})
diff --git a/src/visualizations/config/adapters/dhis_dhis/title/__tests__/singleValue.spec.js b/src/visualizations/config/adapters/dhis_dhis/title/__tests__/singleValue.spec.js
deleted file mode 100644
index 304be7bdb..000000000
--- a/src/visualizations/config/adapters/dhis_dhis/title/__tests__/singleValue.spec.js
+++ /dev/null
@@ -1,21 +0,0 @@
-import getSingleValueTitle from '../singleValue.js'
-
-jest.mock('../../../../../util/getFilterText', () => () => 'The filter text')
-
-describe('getSingleValueTitle', () => {
- it('returns null when layout does not have columns', () => {
- expect(getSingleValueTitle({})).toEqual('')
- })
-
- it('returns the filter text based on column items', () => {
- expect(
- getSingleValueTitle({
- columns: [
- {
- items: [{}],
- },
- ],
- })
- ).toEqual('The filter text')
- })
-})
diff --git a/src/visualizations/config/adapters/dhis_dhis/title/index.js b/src/visualizations/config/adapters/dhis_dhis/title/index.js
deleted file mode 100644
index fb4c6b040..000000000
--- a/src/visualizations/config/adapters/dhis_dhis/title/index.js
+++ /dev/null
@@ -1,30 +0,0 @@
-import { VIS_TYPE_SINGLE_VALUE } from '../../../../../modules/visTypes.js'
-import getFilterText from '../../../../util/getFilterText.js'
-import getSingleValueTitle from './singleValue.js'
-
-function getDefault(layout, metaData, dashboard) {
- return layout.filters && !dashboard
- ? getFilterText(layout.filters, metaData)
- : ''
-}
-
-export default function (layout, metaData, dashboard) {
- if (layout.hideTitle) {
- return ''
- }
-
- if (typeof layout.title === 'string' && layout.title.length) {
- return layout.title
- } else {
- let title
- switch (layout.type) {
- case VIS_TYPE_SINGLE_VALUE:
- title = getSingleValueTitle(layout, metaData)
-
- break
- default:
- title = getDefault(layout, metaData, dashboard)
- }
- return title
- }
-}
diff --git a/src/visualizations/config/adapters/dhis_dhis/type.js b/src/visualizations/config/adapters/dhis_dhis/type.js
deleted file mode 100644
index 412124e58..000000000
--- a/src/visualizations/config/adapters/dhis_dhis/type.js
+++ /dev/null
@@ -1,10 +0,0 @@
-import { VIS_TYPE_SINGLE_VALUE } from '../../../../modules/visTypes.js'
-
-export default function (type) {
- switch (type) {
- case VIS_TYPE_SINGLE_VALUE:
- return { type: VIS_TYPE_SINGLE_VALUE }
- default:
- return { type: VIS_TYPE_SINGLE_VALUE }
- }
-}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/chart/default.js b/src/visualizations/config/adapters/dhis_highcharts/chart/default.js
new file mode 100644
index 000000000..9d4af9829
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/chart/default.js
@@ -0,0 +1,27 @@
+import { getEvents } from '../events/index.js'
+import getType from '../type.js'
+
+const DEFAULT_CHART = {
+ spacingTop: 20,
+ style: {
+ fontFamily: 'Roboto,Helvetica Neue,Helvetica,Arial,sans-serif',
+ },
+}
+
+const DASHBOARD_CHART = {
+ spacingTop: 0,
+ spacingRight: 5,
+ spacingBottom: 2,
+ spacingLeft: 5,
+}
+
+export default function getDefaultChart(layout, el, extraOptions) {
+ return Object.assign(
+ {},
+ getType(layout.type),
+ { renderTo: el || layout.el },
+ DEFAULT_CHART,
+ extraOptions.dashboard ? DASHBOARD_CHART : undefined,
+ getEvents(layout.type)
+ )
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/chart/index.js b/src/visualizations/config/adapters/dhis_highcharts/chart/index.js
new file mode 100644
index 000000000..c6010e016
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/chart/index.js
@@ -0,0 +1,12 @@
+import { VIS_TYPE_SINGLE_VALUE } from '../../../../../modules/visTypes.js'
+import getDefaultChart from './default.js'
+import getSingleValueChart from './singleValue.js'
+
+export default function getChart(layout, el, extraOptions, series) {
+ switch (layout.type) {
+ case VIS_TYPE_SINGLE_VALUE:
+ return getSingleValueChart(layout, el, extraOptions, series)
+ default:
+ return getDefaultChart(layout, el, extraOptions)
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/chart/singleValue.js b/src/visualizations/config/adapters/dhis_highcharts/chart/singleValue.js
new file mode 100644
index 000000000..43a6f66a2
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/chart/singleValue.js
@@ -0,0 +1,19 @@
+import { getSingleValueBackgroundColor } from '../customSVGOptions/singleValue/getSingleValueBackgroundColor.js'
+import getDefaultChart from './default.js'
+
+export default function getSingleValueChart(layout, el, extraOptions, series) {
+ const chart = {
+ ...getDefaultChart(layout, el, extraOptions),
+ backgroundColor: getSingleValueBackgroundColor(
+ layout.legend,
+ extraOptions.legendSets,
+ series[0]
+ ),
+ }
+
+ if (extraOptions.dashboard) {
+ chart.spacingTop = 7
+ }
+
+ return chart
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/index.js b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/index.js
new file mode 100644
index 000000000..ef5b18509
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/index.js
@@ -0,0 +1,29 @@
+import { VIS_TYPE_SINGLE_VALUE } from '../../../../../modules/visTypes.js'
+import getSingleValueCustomSVGOptions from './singleValue/index.js'
+
+export default function getCustomSVGOptions({
+ extraConfig,
+ layout,
+ extraOptions,
+ metaData,
+ series,
+}) {
+ const baseOptions = {
+ visualizationType: layout.type,
+ }
+ switch (layout.type) {
+ case VIS_TYPE_SINGLE_VALUE:
+ return {
+ ...baseOptions,
+ ...getSingleValueCustomSVGOptions({
+ extraConfig,
+ layout,
+ extraOptions,
+ metaData,
+ series,
+ }),
+ }
+ default:
+ break
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueBackgroundColor.js b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueBackgroundColor.js
new file mode 100644
index 000000000..650c895a5
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueBackgroundColor.js
@@ -0,0 +1,17 @@
+import { LEGEND_DISPLAY_STYLE_FILL } from '../../../../../../modules/legends.js'
+import { getSingleValueLegendColor } from './getSingleValueLegendColor.js'
+
+export function getSingleValueBackgroundColor(
+ legendOptions,
+ legendSets,
+ value
+) {
+ const legendColor = getSingleValueLegendColor(
+ legendOptions,
+ legendSets,
+ value
+ )
+ return legendColor && legendOptions.style === LEGEND_DISPLAY_STYLE_FILL
+ ? legendColor
+ : 'transparent'
+}
diff --git a/src/visualizations/config/adapters/dhis_dhis/value/index.js b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueFormattedValue.js
similarity index 69%
rename from src/visualizations/config/adapters/dhis_dhis/value/index.js
rename to src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueFormattedValue.js
index 508f1c9a4..f0b91dee3 100644
--- a/src/visualizations/config/adapters/dhis_dhis/value/index.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueFormattedValue.js
@@ -1,8 +1,9 @@
-import { renderValue } from '../../../../../modules/renderValue.js'
-import { VALUE_TYPE_TEXT } from '../../../../../modules/valueTypes.js'
-import { INDICATOR_FACTOR_100 } from '../index.js'
+import { renderValue } from '../../../../../../modules/renderValue.js'
+import { VALUE_TYPE_TEXT } from '../../../../../../modules/valueTypes.js'
-export default function (value, layout, metaData) {
+export const INDICATOR_FACTOR_100 = 100
+
+export function getSingleValueFormattedValue(value, layout, metaData) {
const valueType = metaData.items[metaData.dimensions.dx[0]].valueType
const indicatorType =
metaData.items[metaData.dimensions.dx[0]].indicatorType
diff --git a/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueLegendColor.js b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueLegendColor.js
new file mode 100644
index 000000000..9f042fc4d
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueLegendColor.js
@@ -0,0 +1,8 @@
+import { getColorByValueFromLegendSet } from '../../../../../../modules/legends.js'
+
+export function getSingleValueLegendColor(legendOptions, legendSets, value) {
+ const legendSet = legendOptions && legendSets[0]
+ return legendSet
+ ? getColorByValueFromLegendSet(legendSet, value)
+ : undefined
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueSubtext.js b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueSubtext.js
new file mode 100644
index 000000000..b14a3f263
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueSubtext.js
@@ -0,0 +1,11 @@
+import { INDICATOR_FACTOR_100 } from './getSingleValueFormattedValue.js'
+
+export function getSingleValueSubtext(metaData) {
+ const indicatorType =
+ metaData.items[metaData.dimensions.dx[0]].indicatorType
+
+ return indicatorType?.displayName &&
+ indicatorType?.factor !== INDICATOR_FACTOR_100
+ ? indicatorType?.displayName
+ : undefined
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueTextColor.js b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueTextColor.js
new file mode 100644
index 000000000..2f3eb0da0
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueTextColor.js
@@ -0,0 +1,27 @@
+import { colors } from '@dhis2/ui'
+import { LEGEND_DISPLAY_STYLE_TEXT } from '../../../../../../modules/legends.js'
+import { shouldUseContrastColor } from '../../../../../util/shouldUseContrastColor.js'
+import { getSingleValueLegendColor } from './getSingleValueLegendColor.js'
+
+export function getSingleValueTextColor(
+ baseColor,
+ value,
+ legendOptions,
+ legendSets
+) {
+ const legendColor = getSingleValueLegendColor(
+ legendOptions,
+ legendSets,
+ value
+ )
+
+ if (!legendColor) {
+ return baseColor
+ }
+
+ if (legendOptions.style === LEGEND_DISPLAY_STYLE_TEXT) {
+ return legendColor
+ }
+
+ return shouldUseContrastColor(legendColor) ? colors.white : baseColor
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueTitleColor.js b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueTitleColor.js
new file mode 100644
index 000000000..bf4f0672b
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/getSingleValueTitleColor.js
@@ -0,0 +1,34 @@
+import { colors } from '@dhis2/ui'
+import { LEGEND_DISPLAY_STYLE_FILL } from '../../../../../../modules/legends.js'
+import { shouldUseContrastColor } from '../../../../../util/shouldUseContrastColor.js'
+import { getSingleValueLegendColor } from './getSingleValueLegendColor.js'
+
+export function getSingleValueTitleColor(
+ customColor,
+ defaultColor,
+ value,
+ legendOptions,
+ legendSets
+) {
+ // Never override custom color
+ if (customColor) {
+ return customColor
+ }
+
+ const isUsingLegendBackground =
+ legendOptions?.style === LEGEND_DISPLAY_STYLE_FILL
+
+ // If not using legend background, always return default color
+ if (!isUsingLegendBackground) {
+ return defaultColor
+ }
+
+ const legendColor = getSingleValueLegendColor(
+ legendOptions,
+ legendSets,
+ value
+ )
+
+ // Return default color or contrasting color when using legend background and default color
+ return shouldUseContrastColor(legendColor) ? colors.white : defaultColor
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/index.js b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/index.js
new file mode 100644
index 000000000..bb0ff56f1
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/customSVGOptions/singleValue/index.js
@@ -0,0 +1,27 @@
+import { colors } from '@dhis2/ui'
+import { getSingleValueFormattedValue } from './getSingleValueFormattedValue.js'
+import { getSingleValueSubtext } from './getSingleValueSubtext.js'
+import { getSingleValueTextColor } from './getSingleValueTextColor.js'
+
+export default function getSingleValueCustomSVGOptions({
+ layout,
+ extraOptions,
+ metaData,
+ series,
+}) {
+ const { dashboard, icon } = extraOptions
+ const value = series[0]
+ return {
+ value,
+ fontColor: getSingleValueTextColor(
+ colors.grey900,
+ value,
+ layout.legend,
+ extraOptions.legendSets
+ ),
+ formattedValue: getSingleValueFormattedValue(value, layout, metaData),
+ icon,
+ dashboard,
+ subText: getSingleValueSubtext(metaData),
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/chart.js b/src/visualizations/config/adapters/dhis_highcharts/events/index.js
similarity index 51%
rename from src/visualizations/config/adapters/dhis_highcharts/chart.js
rename to src/visualizations/config/adapters/dhis_highcharts/events/index.js
index e50a52ca9..4f8bf0904 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/chart.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/index.js
@@ -1,20 +1,6 @@
-import getType from './type.js'
+import loadCustomSVG from './loadCustomSVG/index.js'
-const DEFAULT_CHART = {
- spacingTop: 20,
- style: {
- fontFamily: 'Roboto,Helvetica Neue,Helvetica,Arial,sans-serif',
- },
-}
-
-const DASHBOARD_CHART = {
- spacingTop: 0,
- spacingRight: 5,
- spacingBottom: 2,
- spacingLeft: 5,
-}
-
-const getEvents = () => ({
+export const getEvents = (visType) => ({
events: {
load: function () {
// Align legend icon with legend text
@@ -31,17 +17,7 @@ const getEvents = () => ({
})
}
})
+ loadCustomSVG.call(this, visType)
},
},
})
-
-export default function (layout, el, dashboard) {
- return Object.assign(
- {},
- getType(layout.type),
- { renderTo: el || layout.el },
- DEFAULT_CHART,
- dashboard ? DASHBOARD_CHART : undefined,
- getEvents()
- )
-}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/index.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/index.js
new file mode 100644
index 000000000..6e01df566
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/index.js
@@ -0,0 +1,12 @@
+import { VIS_TYPE_SINGLE_VALUE } from '../../../../../../modules/visTypes.js'
+import loadSingleValueSVG from './singleValue/index.js'
+
+export default function loadCustomSVG(visType) {
+ switch (visType) {
+ case VIS_TYPE_SINGLE_VALUE:
+ loadSingleValueSVG.call(this)
+ break
+ default:
+ break
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/addIconElement.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/addIconElement.js
new file mode 100644
index 000000000..dfa2c0c57
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/addIconElement.js
@@ -0,0 +1,32 @@
+const parser = new DOMParser()
+
+export function addIconElement(svgString, color) {
+ const svgIconDocument = parser.parseFromString(svgString, 'image/svg+xml')
+ const iconElHeight = svgIconDocument.documentElement.getAttribute('height')
+ const iconElWidth = svgIconDocument.documentElement.getAttribute('width')
+ const iconGroup = this.renderer
+ .g('icon')
+ .attr({ color, 'data-test': 'visualization-icon' })
+ .css({
+ visibility: 'hidden',
+ })
+
+ /* Force the group element to have the same dimensions as the original
+ * SVG image by adding this rect. This ensures the icon has the intended
+ * whitespace around it and makes scaling and translating easier. */
+ this.renderer.rect(0, 0, iconElWidth, iconElHeight).add(iconGroup)
+
+ Array.from(svgIconDocument.documentElement.children).forEach((pathNode) => {
+ /* It is also possible to use the SVGRenderer to draw the icon but that
+ * approach is more error prone, so during review it was decided to just
+ * append the SVG children to the iconGroup using native the native DOM
+ * API. For reference see this commit, for an implementation using the
+ * SVVGRenderer:
+ * https://github.com/dhis2/analytics/pull/1698/commits/f95bee838e07f4cdfc3cab6e92f28f49a386a0ad */
+ iconGroup.element.appendChild(pathNode)
+ })
+
+ iconGroup.add()
+
+ return iconGroup
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/checkIfFitsWithinContainer.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/checkIfFitsWithinContainer.js
new file mode 100644
index 000000000..182611977
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/checkIfFitsWithinContainer.js
@@ -0,0 +1,29 @@
+import { ACTUAL_NUMBER_HEIGHT_FACTOR } from './constants.js'
+
+export function checkIfFitsWithinContainer(
+ availableSpace,
+ valueElement,
+ subTextElement,
+ icon,
+ subText,
+ spacing
+) {
+ const valueRect = valueElement.getBBox(true)
+ const subTextRect = subText
+ ? subTextElement.getBBox(true)
+ : { width: 0, height: 0 }
+ const requiredValueWidth = icon
+ ? valueRect.width + spacing.iconGap + spacing.iconSize
+ : valueRect.width
+ const requiredHeight = subText
+ ? valueRect.height * ACTUAL_NUMBER_HEIGHT_FACTOR +
+ spacing.subTextTop +
+ subTextRect.height
+ : valueRect.height * ACTUAL_NUMBER_HEIGHT_FACTOR
+ const fitsHorizontally =
+ availableSpace.width > requiredValueWidth &&
+ availableSpace.width > subTextRect.width
+ const fitsVertically = availableSpace.height > requiredHeight
+
+ return fitsHorizontally && fitsVertically
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/computeLayoutRect.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/computeLayoutRect.js
new file mode 100644
index 000000000..a5d2705c9
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/computeLayoutRect.js
@@ -0,0 +1,43 @@
+import { computeSpacingTop } from './computeSpacingTop.js'
+import { ACTUAL_NUMBER_HEIGHT_FACTOR } from './constants.js'
+
+export function computeLayoutRect(
+ valueElement,
+ subTextElement,
+ iconElement,
+ spacing
+) {
+ const valueRect = valueElement.getBBox()
+ const containerCenterY = this.chartHeight / 2
+ const containerCenterX = this.chartWidth / 2
+ const minY = computeSpacingTop.call(this, spacing.valueTop)
+
+ let width = valueRect.width
+ let height = valueRect.height * ACTUAL_NUMBER_HEIGHT_FACTOR
+ let sideMarginTop = 0
+ let sideMarginBottom = 0
+
+ if (iconElement) {
+ width += spacing.iconGap + spacing.iconSize
+ }
+
+ if (subTextElement) {
+ const subTextRect = subTextElement.getBBox()
+ if (subTextRect.width > width) {
+ sideMarginTop = (subTextRect.width - width) / 2
+ width = subTextRect.width
+ } else {
+ sideMarginBottom = (width - subTextRect.width) / 2
+ }
+ height += spacing.subTextTop + subTextRect.height
+ }
+
+ return {
+ x: containerCenterX - width / 2,
+ y: Math.max(containerCenterY - height / 2, minY),
+ width,
+ height,
+ sideMarginTop,
+ sideMarginBottom,
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/computeSpacingTop.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/computeSpacingTop.js
new file mode 100644
index 000000000..1de00c836
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/computeSpacingTop.js
@@ -0,0 +1,15 @@
+export function computeSpacingTop(valueSpacingTop) {
+ if (this.subtitle.textStr) {
+ /* If a subtitle is present this will be below the title so base
+ * the value X position on this */
+ const subTitleRect = this.subtitle.element.getBBox()
+ return subTitleRect.y + subTitleRect.height + valueSpacingTop
+ } else if (this.title.textStr) {
+ // Otherwise base on title
+ const titleRect = this.title.element.getBBox()
+ return titleRect.y + titleRect.height + valueSpacingTop
+ } else {
+ // If neither are present only adjust for valueSpacingTop
+ return valueSpacingTop
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/constants.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/constants.js
new file mode 100644
index 000000000..b76e26a44
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/constants.js
@@ -0,0 +1,4 @@
+// multiply value text size with this factor
+// to get very close to the actual number height
+// as numbers don't go below the baseline like e.g. "j" and "g"
+export const ACTUAL_NUMBER_HEIGHT_FACTOR = 2 / 3
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/getAvailableSpace.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/getAvailableSpace.js
new file mode 100644
index 000000000..c9f567f4c
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/getAvailableSpace.js
@@ -0,0 +1,10 @@
+import { computeSpacingTop } from './computeSpacingTop.js'
+import { MIN_SIDE_WHITESPACE } from './styles.js'
+
+export function getAvailableSpace(valueSpacingTop) {
+ return {
+ height:
+ this.chartHeight - computeSpacingTop.call(this, valueSpacingTop),
+ width: this.chartWidth - MIN_SIDE_WHITESPACE * 2,
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/index.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/index.js
new file mode 100644
index 000000000..84cc83e7d
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/index.js
@@ -0,0 +1,55 @@
+import { addIconElement } from './addIconElement.js'
+import { checkIfFitsWithinContainer } from './checkIfFitsWithinContainer.js'
+import { getAvailableSpace } from './getAvailableSpace.js'
+import { positionElements } from './positionElements.js'
+import { DynamicStyles } from './styles.js'
+
+export default function loadSingleValueSVG() {
+ const { formattedValue, icon, subText, fontColor } =
+ this.userOptions.customSVGOptions
+ const dynamicStyles = new DynamicStyles(this.userOptions?.isPdfExport)
+ const valueElement = this.renderer
+ .text(formattedValue)
+ .attr('data-test', 'visualization-primary-value')
+ .css({ color: fontColor, visibility: 'hidden' })
+ .add()
+ const subTextElement = subText
+ ? this.renderer
+ .text(subText)
+ .attr('data-test', 'visualization-subtext')
+ .css({ color: fontColor, visibility: 'hidden' })
+ .add()
+ : null
+ const iconElement = icon ? addIconElement.call(this, icon, fontColor) : null
+
+ let fitsWithinContainer = false
+ let styles = {}
+
+ while (!fitsWithinContainer && dynamicStyles.hasNext()) {
+ styles = dynamicStyles.next()
+
+ valueElement.css(styles.value)
+ subTextElement?.css(styles.subText)
+
+ fitsWithinContainer = checkIfFitsWithinContainer(
+ getAvailableSpace.call(this, styles.spacing.valueTop),
+ valueElement,
+ subTextElement,
+ icon,
+ subText,
+ styles.spacing
+ )
+ }
+
+ positionElements.call(
+ this,
+ valueElement,
+ subTextElement,
+ iconElement,
+ styles.spacing
+ )
+
+ valueElement.css({ visibility: 'visible' })
+ iconElement?.css({ visibility: 'visible' })
+ subTextElement?.css({ visibility: 'visible' })
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/positionElements.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/positionElements.js
new file mode 100644
index 000000000..052c86b5b
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/positionElements.js
@@ -0,0 +1,62 @@
+import { computeLayoutRect } from './computeLayoutRect.js'
+import { ACTUAL_NUMBER_HEIGHT_FACTOR } from './constants.js'
+
+export function positionElements(
+ valueElement,
+ subTextElement,
+ iconElement,
+ spacing
+) {
+ const valueElementBox = valueElement.getBBox()
+ /* Layout here refers to a virtual rect that wraps
+ * all indiviual parts of the single value visualization
+ * (value, subtext and icon) */
+ const layoutRect = computeLayoutRect.call(
+ this,
+ valueElement,
+ subTextElement,
+ iconElement,
+ spacing
+ )
+
+ valueElement.align(
+ {
+ align: 'right',
+ verticalAlign: 'top',
+ alignByTranslate: false,
+ x: (valueElementBox.width + layoutRect.sideMarginTop) * -1,
+ y: valueElementBox.height * ACTUAL_NUMBER_HEIGHT_FACTOR,
+ },
+ false,
+ layoutRect
+ )
+
+ if (iconElement) {
+ const { height } = iconElement.getBBox()
+ const scale = spacing.iconSize / height
+ const translateX = layoutRect.x + layoutRect.sideMarginTop
+ const iconHeight = height * scale
+ const valueElementHeight =
+ valueElementBox.height * ACTUAL_NUMBER_HEIGHT_FACTOR
+ const translateY = layoutRect.y + (valueElementHeight - iconHeight) / 2
+
+ /* The icon is a with elements that contain coordinates.
+ * These path-coordinates only scale correctly when using CSS translate */
+ iconElement.css({
+ transform: `translate(${translateX}px, ${translateY}px) scale(${scale})`,
+ })
+ }
+
+ if (subTextElement) {
+ subTextElement.align(
+ {
+ align: 'left',
+ verticalAlign: 'bottom',
+ alignByTranslate: false,
+ x: layoutRect.sideMarginBottom,
+ },
+ false,
+ layoutRect
+ )
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/styles.js b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/styles.js
new file mode 100644
index 000000000..f1b944ee2
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/events/loadCustomSVG/singleValue/styles.js
@@ -0,0 +1,62 @@
+const valueStyles = [
+ { 'font-size': '164px', 'letter-spacing': '-5px' },
+ { 'font-size': '128px', 'letter-spacing': '-4px' },
+ { 'font-size': '96px', 'letter-spacing': '-3px' },
+ { 'font-size': '64px', 'letter-spacing': '-2.5px' },
+ { 'font-size': '40px', 'letter-spacing': '-1.5px' },
+ { 'font-size': '20px', 'letter-spacing': '-1px' },
+]
+
+const subTextStyles = [
+ { 'font-size': '36px', 'letter-spacing': '-1.4px' },
+ { 'font-size': '32px', 'letter-spacing': '-1.2px' },
+ { 'font-size': '26px', 'letter-spacing': '-0.8px' },
+ { 'font-size': '20px', 'letter-spacing': '-0.6px' },
+ { 'font-size': '14px', 'letter-spacing': '0.2px' },
+ { 'font-size': '9px', 'letter-spacing': '0px' },
+]
+
+const spacings = [
+ { valueTop: 8, subTextTop: 12, iconGap: 8, iconSize: 164 },
+ { valueTop: 8, subTextTop: 12, iconGap: 6, iconSize: 128 },
+ { valueTop: 8, subTextTop: 8, iconGap: 4, iconSize: 96 },
+ { valueTop: 8, subTextTop: 8, iconGap: 4, iconSize: 64 },
+ { valueTop: 8, subTextTop: 8, iconGap: 4, iconSize: 40 },
+ { valueTop: 8, subTextTop: 4, iconGap: 2, iconSize: 20 },
+]
+
+export const MIN_SIDE_WHITESPACE = 4
+
+export class DynamicStyles {
+ constructor(isPdfExport) {
+ this.currentIndex = 0
+ this.isPdfExport = isPdfExport
+ }
+ getStyle() {
+ return {
+ value: {
+ ...valueStyles[this.currentIndex],
+ 'font-weight': this.isPdfExport ? 'normal' : '300',
+ },
+ subText: subTextStyles[this.currentIndex],
+ spacing: spacings[this.currentIndex],
+ }
+ }
+ next() {
+ if (this.currentIndex === valueStyles.length - 1) {
+ throw new Error('No next available, already on the smallest style')
+ } else {
+ ++this.currentIndex
+ }
+
+ return this.getStyle()
+ }
+ first() {
+ this.currentIndex = 0
+
+ return this.getStyle()
+ }
+ hasNext() {
+ return this.currentIndex < valueStyles.length - 1
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/exporting.js b/src/visualizations/config/adapters/dhis_highcharts/exporting.js
new file mode 100644
index 000000000..032a9c689
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/exporting.js
@@ -0,0 +1,25 @@
+import { VIS_TYPE_SINGLE_VALUE } from '../../../../modules/visTypes.js'
+import loadSingleValueSVG from './events/loadCustomSVG/singleValue/index.js'
+
+export default function getExporting(visType) {
+ const exporting = {
+ // disable exporting context menu
+ enabled: false,
+ }
+ switch (visType) {
+ case VIS_TYPE_SINGLE_VALUE:
+ return {
+ ...exporting,
+ chartOptions: {
+ chart: {
+ events: {
+ load: loadSingleValueSVG,
+ },
+ },
+ },
+ }
+
+ default:
+ return exporting
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/index.js b/src/visualizations/config/adapters/dhis_highcharts/index.js
index 29ecf41c0..0f3ddb271 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/index.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/index.js
@@ -14,10 +14,13 @@ import {
} from '../../../../modules/visTypes.js'
import { defaultMultiAxisTheme1 } from '../../../util/colors/themes.js'
import addTrendLines, { isRegressionIneligible } from './addTrendLines.js'
-import getChart from './chart.js'
+import getChart from './chart/index.js'
+import getCustomSVGOptions from './customSVGOptions/index.js'
+import getExporting from './exporting.js'
import getScatterData from './getScatterData.js'
import getSortedConfig from './getSortedConfig.js'
import getTrimmedConfig from './getTrimmedConfig.js'
+import getLang from './lang.js'
import getLegend from './legend.js'
import { applyLegendSet, getLegendSetTooltip } from './legendSet.js'
import getNoData from './noData.js'
@@ -77,21 +80,17 @@ export default function ({ store, layout, el, extraConfig, extraOptions }) {
let config = {
// type etc
- chart: getChart(_layout, el, _extraOptions.dashboard),
+ chart: getChart(_layout, el, _extraOptions, series),
// title
- title: getTitle(
- _layout,
- store.data[0].metaData,
- _extraOptions.dashboard
- ),
+ title: getTitle(_layout, store.data[0].metaData, _extraOptions, series),
// subtitle
subtitle: getSubtitle(
series,
_layout,
store.data[0].metaData,
- _extraOptions.dashboard
+ _extraOptions
),
// x-axis
@@ -123,11 +122,8 @@ export default function ({ store, layout, el, extraConfig, extraOptions }) {
pane: getPane(_layout.type),
// no data + zoom
- lang: {
- noData: _extraOptions.noData.text,
- resetZoom: _extraOptions.resetZoom.text,
- },
- noData: getNoData(),
+ lang: getLang(_layout.type, _extraOptions),
+ noData: getNoData(_layout.type),
// credits
credits: {
@@ -135,10 +131,20 @@ export default function ({ store, layout, el, extraConfig, extraOptions }) {
},
// exporting
- exporting: {
- // disable exporting context menu
- enabled: false,
- },
+ exporting: getExporting(_layout.type),
+
+ /* The config object passed to the Highcharts Chart constructor
+ * can contain arbitrary properties, which are made accessible
+ * under the Chart instance's `userOptions` member. This means
+ * that in event callback functions the custom SVG options are
+ * accessible as `this.userOptions.customSVGOptions` */
+ customSVGOptions: getCustomSVGOptions({
+ extraConfig,
+ layout: _layout,
+ extraOptions: _extraOptions,
+ metaData: store.data[0].metaData,
+ series,
+ }),
}
// get plot options for scatter
@@ -234,5 +240,7 @@ export default function ({ store, layout, el, extraConfig, extraOptions }) {
// force apply extra config
Object.assign(config, extraConfig)
+ console.log(objectClean(config))
+
return objectClean(config)
}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/lang.js b/src/visualizations/config/adapters/dhis_highcharts/lang.js
new file mode 100644
index 000000000..80299fe41
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/lang.js
@@ -0,0 +1,15 @@
+import { VIS_TYPE_SINGLE_VALUE } from '../../../../modules/visTypes.js'
+
+export default function getLang(visType, extraOptions) {
+ return {
+ /* The SingleValue visualization consists of some custom SVG elements
+ * rendered on an empty chart. Since the chart is empty, there is never
+ * any data and Highcharts will show the noData text. To avoid this we
+ * clear the text here. */
+ noData:
+ visType === VIS_TYPE_SINGLE_VALUE
+ ? undefined
+ : extraOptions.noData.text,
+ resetZoom: extraOptions.resetZoom.text,
+ }
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/plotOptions.js b/src/visualizations/config/adapters/dhis_highcharts/plotOptions.js
index 928019506..e9e775096 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/plotOptions.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/plotOptions.js
@@ -79,6 +79,6 @@ export default ({
}
: {}
default:
- return {}
+ return null
}
}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/series/index.js b/src/visualizations/config/adapters/dhis_highcharts/series/index.js
index e4d4eae67..e4ec840f0 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/series/index.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/series/index.js
@@ -9,6 +9,7 @@ import {
isYearOverYear,
VIS_TYPE_LINE,
VIS_TYPE_SCATTER,
+ VIS_TYPE_SINGLE_VALUE,
} from '../../../../../modules/visTypes.js'
import { getAxisStringFromId } from '../../../../util/axisId.js'
import {
@@ -225,6 +226,9 @@ export default function ({
displayStrategy,
}) {
switch (layout.type) {
+ case VIS_TYPE_SINGLE_VALUE:
+ series = []
+ break
case VIS_TYPE_PIE:
series = getPie(
series,
@@ -249,7 +253,7 @@ export default function ({
})
}
- series.forEach((seriesObj) => {
+ series?.forEach((seriesObj) => {
// animation
seriesObj.animation = {
duration: getAnimation(
diff --git a/src/visualizations/config/adapters/dhis_highcharts/subtitle/__tests__/singleValue.spec.js b/src/visualizations/config/adapters/dhis_highcharts/subtitle/__tests__/singleValue.spec.js
new file mode 100644
index 000000000..c7baa2ad6
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/subtitle/__tests__/singleValue.spec.js
@@ -0,0 +1,64 @@
+import getSingleValueSubtitle from '../singleValue.js'
+
+jest.mock(
+ '../../../../../util/getFilterText',
+ () => () => 'The default filter text'
+)
+
+describe('getSingleValueSubtitle', () => {
+ it('returns empty subtitle when flag hideSubtitle exists', () => {
+ expect(getSingleValueSubtitle({ hideSubtitle: true })).toEqual('')
+ })
+
+ it('returns the subtitle provided in the layout', () => {
+ const subtitle = 'The subtitle was already set'
+ expect(getSingleValueSubtitle({ subtitle })).toEqual(subtitle)
+ })
+
+ it('returns an empty string when layout does not have filters', () => {
+ expect(getSingleValueSubtitle({})).toEqual('')
+ })
+
+ it('returns the filter text', () => {
+ expect(getSingleValueSubtitle({ filters: [] })).toEqual(
+ 'The default filter text'
+ )
+ })
+
+ describe('not dashboard', () => {
+ describe('layout does not include title', () => {
+ it('returns empty subtitle', () => {
+ expect(
+ getSingleValueSubtitle({ filters: undefined }, {}, false)
+ ).toEqual('')
+ })
+ })
+
+ /* All these tests have been moved and adjusted from here:
+ * src/visualizations/config/adapters/dhis_dhis/title/__tests__`
+ * The test below asserted the default subtitle behaviour, for
+ * visualization types other than SingleValue. It expected that
+ * the title was being used as subtitle. It fails now, and I
+ * believe that this behaviour does not make sense. So instead
+ * of fixing it, I disabled it. */
+ // describe('layout includes title', () => {
+ // it('returns filter title as subtitle', () => {
+ // expect(
+ // getSingleValueSubtitle(
+ // { filters: undefined, title: 'Chart title' },
+ // {},
+ // false
+ // )
+ // ).toEqual('The default filter text')
+ // })
+ // })
+ })
+
+ describe('dashboard', () => {
+ it('returns filter title as subtitle', () => {
+ expect(getSingleValueSubtitle({ filters: {} }, {}, true)).toEqual(
+ 'The default filter text'
+ )
+ })
+ })
+})
diff --git a/src/visualizations/config/adapters/dhis_highcharts/subtitle/index.js b/src/visualizations/config/adapters/dhis_highcharts/subtitle/index.js
index 9d2dc1bc7..6509c3e5a 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/subtitle/index.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/subtitle/index.js
@@ -7,16 +7,21 @@ import {
FONT_STYLE_OPTION_TEXT_ALIGN,
FONT_STYLE_VISUALIZATION_SUBTITLE,
mergeFontStyleWithDefault,
+ defaultFontStyle,
} from '../../../../../modules/fontStyle.js'
import {
VIS_TYPE_YEAR_OVER_YEAR_LINE,
VIS_TYPE_YEAR_OVER_YEAR_COLUMN,
isVerticalType,
VIS_TYPE_SCATTER,
+ VIS_TYPE_SINGLE_VALUE,
} from '../../../../../modules/visTypes.js'
import getFilterText from '../../../../util/getFilterText.js'
import { getTextAlignOption } from '../getTextAlignOption.js'
import getYearOverYearTitle from '../title/yearOverYear.js'
+import getSingleValueSubtitle, {
+ getSingleValueSubtitleColor,
+} from './singleValue.js'
const DASHBOARD_SUBTITLE = {
style: {
@@ -31,23 +36,48 @@ const DASHBOARD_SUBTITLE = {
}
function getDefault(layout, dashboard, filterTitle) {
- return {
- text: dashboard || isString(layout.title) ? filterTitle : undefined,
- }
+ return dashboard || isString(layout.title) ? filterTitle : undefined
}
-export default function (series, layout, metaData, dashboard) {
+export default function (series, layout, metaData, extraOptions) {
+ if (layout.hideSubtitle) {
+ return null
+ }
+
+ const { dashboard, legendSets } = extraOptions
+ const legendOptions = layout.legend
const fontStyle = mergeFontStyleWithDefault(
layout.fontStyle && layout.fontStyle[FONT_STYLE_VISUALIZATION_SUBTITLE],
FONT_STYLE_VISUALIZATION_SUBTITLE
)
- let subtitle = {
- text: undefined,
- }
-
- if (layout.hideSubtitle) {
- return null
- }
+ const subtitle = Object.assign(
+ {
+ text: undefined,
+ },
+ dashboard
+ ? DASHBOARD_SUBTITLE
+ : {
+ align: getTextAlignOption(
+ fontStyle[FONT_STYLE_OPTION_TEXT_ALIGN],
+ FONT_STYLE_VISUALIZATION_SUBTITLE,
+ isVerticalType(layout.type)
+ ),
+ style: {
+ // DHIS2-578: dynamically truncate subtitle when it's taking more than 1 line
+ color: undefined,
+ fontSize: `${fontStyle[FONT_STYLE_OPTION_FONT_SIZE]}px`,
+ fontWeight: fontStyle[FONT_STYLE_OPTION_BOLD]
+ ? FONT_STYLE_OPTION_BOLD
+ : 'normal',
+ fontStyle: fontStyle[FONT_STYLE_OPTION_ITALIC]
+ ? FONT_STYLE_OPTION_ITALIC
+ : 'normal',
+ whiteSpace: 'nowrap',
+ overflow: 'hidden',
+ textOverflow: 'ellipsis',
+ },
+ }
+ )
// DHIS2-578: allow for optional custom subtitle
const customSubtitle =
@@ -59,6 +89,9 @@ export default function (series, layout, metaData, dashboard) {
const filterTitle = getFilterText(layout.filters, metaData)
switch (layout.type) {
+ case VIS_TYPE_SINGLE_VALUE:
+ subtitle.text = getSingleValueSubtitle(layout, metaData)
+ break
case VIS_TYPE_YEAR_OVER_YEAR_LINE:
case VIS_TYPE_YEAR_OVER_YEAR_COLUMN:
subtitle.text = getYearOverYearTitle(
@@ -71,37 +104,46 @@ export default function (series, layout, metaData, dashboard) {
subtitle.text = filterTitle
break
default:
- subtitle = getDefault(layout, dashboard, filterTitle)
+ subtitle.text = getDefault(layout, dashboard, filterTitle)
}
}
+ switch (layout.type) {
+ case VIS_TYPE_SINGLE_VALUE:
+ {
+ const defaultColor =
+ defaultFontStyle?.[FONT_STYLE_VISUALIZATION_SUBTITLE]?.[
+ FONT_STYLE_OPTION_TEXT_COLOR
+ ]
+ const customColor =
+ layout?.fontStyle?.[FONT_STYLE_VISUALIZATION_SUBTITLE]?.[
+ FONT_STYLE_OPTION_TEXT_COLOR
+ ]
+ subtitle.style.color = getSingleValueSubtitleColor(
+ customColor,
+ defaultColor,
+ series[0],
+ legendOptions,
+ legendSets
+ )
+ if (dashboard) {
+ // Single value subtitle text should be multiline
+ /* TODO: The default color of the subtitle now is #4a5768 but the
+ * original implementation used #666, which is a lighter grey.
+ * If we want to keep this color, changes are needed here. */
+ Object.assign(subtitle.style, {
+ wordWrap: 'normal',
+ whiteSpace: 'normal',
+ overflow: 'visible',
+ textOverflow: 'initial',
+ })
+ }
+ }
+ break
+ default:
+ subtitle.style.color = fontStyle[FONT_STYLE_OPTION_TEXT_COLOR]
+ break
+ }
+
return subtitle
- ? Object.assign(
- {},
- dashboard
- ? DASHBOARD_SUBTITLE
- : {
- align: getTextAlignOption(
- fontStyle[FONT_STYLE_OPTION_TEXT_ALIGN],
- FONT_STYLE_VISUALIZATION_SUBTITLE,
- isVerticalType(layout.type)
- ),
- style: {
- // DHIS2-578: dynamically truncate subtitle when it's taking more than 1 line
- color: fontStyle[FONT_STYLE_OPTION_TEXT_COLOR],
- fontSize: `${fontStyle[FONT_STYLE_OPTION_FONT_SIZE]}px`,
- fontWeight: fontStyle[FONT_STYLE_OPTION_BOLD]
- ? FONT_STYLE_OPTION_BOLD
- : 'normal',
- fontStyle: fontStyle[FONT_STYLE_OPTION_ITALIC]
- ? FONT_STYLE_OPTION_ITALIC
- : 'normal',
- whiteSpace: 'nowrap',
- overflow: 'hidden',
- textOverflow: 'ellipsis',
- },
- },
- subtitle
- )
- : subtitle
}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/subtitle/singleValue.js b/src/visualizations/config/adapters/dhis_highcharts/subtitle/singleValue.js
new file mode 100644
index 000000000..922f142cf
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/subtitle/singleValue.js
@@ -0,0 +1,18 @@
+import getFilterText from '../../../../util/getFilterText.js'
+export { getSingleValueTitleColor as getSingleValueSubtitleColor } from '../customSVGOptions/singleValue/getSingleValueTitleColor.js'
+
+export default function getSingleValueSubtitle(layout, metaData) {
+ if (layout.hideSubtitle || 1 === 0) {
+ return ''
+ }
+
+ if (typeof layout.subtitle === 'string' && layout.subtitle.length) {
+ return layout.subtitle
+ }
+
+ if (layout.filters) {
+ return getFilterText(layout.filters, metaData)
+ }
+
+ return ''
+}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/title/__tests__/singleValue.spec.js b/src/visualizations/config/adapters/dhis_highcharts/title/__tests__/singleValue.spec.js
new file mode 100644
index 000000000..bc8022f81
--- /dev/null
+++ b/src/visualizations/config/adapters/dhis_highcharts/title/__tests__/singleValue.spec.js
@@ -0,0 +1,57 @@
+import { getSingleValueTitleText } from '../singleValue.js'
+
+jest.mock('../../../../../util/getFilterText', () => () => 'The filter text')
+
+describe('getSingleValueTitle', () => {
+ it('returns empty title when flag hideTitle exists', () => {
+ expect(getSingleValueTitleText({ hideTitle: true })).toEqual('')
+ })
+
+ it('returns the title provided in the layout', () => {
+ const title = 'The title was already set'
+ expect(getSingleValueTitleText({ title })).toEqual(title)
+ })
+
+ it('returns null when layout does not have columns', () => {
+ expect(getSingleValueTitleText({})).toEqual('')
+ })
+
+ it('returns the filter text based on column items', () => {
+ expect(
+ getSingleValueTitleText({
+ columns: [
+ {
+ items: [{}],
+ },
+ ],
+ })
+ ).toEqual('The filter text')
+ })
+
+ describe('not dashboard', () => {
+ it('returns filter text as title', () => {
+ expect(
+ getSingleValueTitleText(
+ {
+ columns: [
+ {
+ items: [{}],
+ },
+ ],
+ filters: [],
+ },
+ {},
+ false
+ )
+ ).toEqual('The filter text')
+ })
+ })
+
+ describe('dashboard', () => {
+ it('returns empty string', () => {
+ expect(getSingleValueTitleText({ filters: {} }, {}, true)).toEqual(
+ ''
+ )
+ })
+ })
+})
diff --git a/src/visualizations/config/adapters/dhis_highcharts/title/index.js b/src/visualizations/config/adapters/dhis_highcharts/title/index.js
index e4e4f1a4a..7a86ec47f 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/title/index.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/title/index.js
@@ -7,6 +7,7 @@ import {
FONT_STYLE_OPTION_TEXT_ALIGN,
FONT_STYLE_VISUALIZATION_TITLE,
mergeFontStyleWithDefault,
+ defaultFontStyle,
} from '../../../../../modules/fontStyle.js'
import {
VIS_TYPE_YEAR_OVER_YEAR_LINE,
@@ -14,10 +15,15 @@ import {
VIS_TYPE_GAUGE,
isVerticalType,
VIS_TYPE_SCATTER,
+ VIS_TYPE_SINGLE_VALUE,
} from '../../../../../modules/visTypes.js'
import getFilterText from '../../../../util/getFilterText.js'
import { getTextAlignOption } from '../getTextAlignOption.js'
import getScatterTitle from './scatter.js'
+import {
+ getSingleValueTitleColor,
+ getSingleValueTitleText,
+} from './singleValue.js'
import getYearOverYearTitle from './yearOverYear.js'
const DASHBOARD_TITLE_STYLE = {
@@ -41,42 +47,22 @@ function getDefault(layout, metaData, dashboard) {
return null
}
-export default function (layout, metaData, dashboard) {
+export default function (layout, metaData, extraOptions, series) {
+ if (layout.hideTitle) {
+ return {
+ text: undefined,
+ }
+ }
+ const { dashboard, legendSets } = extraOptions
+ const legendOptions = layout.legend
const fontStyle = mergeFontStyleWithDefault(
layout.fontStyle && layout.fontStyle[FONT_STYLE_VISUALIZATION_TITLE],
FONT_STYLE_VISUALIZATION_TITLE
)
-
- const title = {
- text: undefined,
- }
-
- if (layout.hideTitle) {
- return title
- }
-
- const customTitle = (layout.title && layout.displayTitle) || layout.title
-
- if (isString(customTitle) && customTitle.length) {
- title.text = customTitle
- } else {
- switch (layout.type) {
- case VIS_TYPE_GAUGE:
- case VIS_TYPE_YEAR_OVER_YEAR_LINE:
- case VIS_TYPE_YEAR_OVER_YEAR_COLUMN:
- title.text = getYearOverYearTitle(layout, metaData, dashboard)
- break
- case VIS_TYPE_SCATTER:
- title.text = getScatterTitle(layout, metaData, dashboard)
- break
- default:
- title.text = getDefault(layout, metaData, dashboard)
- break
- }
- }
-
- return Object.assign(
- {},
+ const title = Object.assign(
+ {
+ text: undefined,
+ },
dashboard
? DASHBOARD_TITLE_STYLE
: {
@@ -87,7 +73,7 @@ export default function (layout, metaData, dashboard) {
isVerticalType(layout.type)
),
style: {
- color: fontStyle[FONT_STYLE_OPTION_TEXT_COLOR],
+ color: undefined,
fontSize: `${fontStyle[FONT_STYLE_OPTION_FONT_SIZE]}px`,
fontWeight: fontStyle[FONT_STYLE_OPTION_BOLD]
? FONT_STYLE_OPTION_BOLD
@@ -99,7 +85,65 @@ export default function (layout, metaData, dashboard) {
overflow: 'hidden',
textOverflow: 'ellipsis',
},
- },
- title
+ }
)
+
+ const customTitleText =
+ (layout.title && layout.displayTitle) || layout.title
+
+ if (isString(customTitleText) && customTitleText.length) {
+ title.text = customTitleText
+ } else {
+ switch (layout.type) {
+ case VIS_TYPE_SINGLE_VALUE:
+ title.text = getSingleValueTitleText(
+ layout,
+ metaData,
+ dashboard
+ )
+ break
+ case VIS_TYPE_GAUGE:
+ case VIS_TYPE_YEAR_OVER_YEAR_LINE:
+ case VIS_TYPE_YEAR_OVER_YEAR_COLUMN:
+ title.text = getYearOverYearTitle(layout, metaData, dashboard)
+ break
+ case VIS_TYPE_SCATTER:
+ title.text = getScatterTitle(layout, metaData, dashboard)
+ break
+ default:
+ title.text = getDefault(layout, metaData, dashboard)
+ break
+ }
+ }
+
+ switch (layout.type) {
+ case VIS_TYPE_SINGLE_VALUE:
+ {
+ const defaultColor =
+ defaultFontStyle?.[FONT_STYLE_VISUALIZATION_TITLE]?.[
+ FONT_STYLE_OPTION_TEXT_COLOR
+ ]
+ const customColor =
+ layout?.fontStyle?.[FONT_STYLE_VISUALIZATION_TITLE]?.[
+ FONT_STYLE_OPTION_TEXT_COLOR
+ ]
+ title.style.color = getSingleValueTitleColor(
+ customColor,
+ defaultColor,
+ series[0],
+ legendOptions,
+ legendSets
+ )
+ if (dashboard) {
+ // TODO: is this always what we want?
+ title.style.fontWeight = 'normal'
+ }
+ }
+ break
+ default:
+ title.style.color = fontStyle[FONT_STYLE_OPTION_TEXT_COLOR]
+ break
+ }
+
+ return title
}
diff --git a/src/visualizations/config/adapters/dhis_dhis/title/singleValue.js b/src/visualizations/config/adapters/dhis_highcharts/title/singleValue.js
similarity index 50%
rename from src/visualizations/config/adapters/dhis_dhis/title/singleValue.js
rename to src/visualizations/config/adapters/dhis_highcharts/title/singleValue.js
index 802c866c0..fdf5d891a 100644
--- a/src/visualizations/config/adapters/dhis_dhis/title/singleValue.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/title/singleValue.js
@@ -1,6 +1,15 @@
import getFilterText from '../../../../util/getFilterText.js'
+export { getSingleValueTitleColor } from '../customSVGOptions/singleValue/getSingleValueTitleColor.js'
+
+export function getSingleValueTitleText(layout, metaData) {
+ if (layout.hideTitle) {
+ return ''
+ }
+
+ if (typeof layout.title === 'string' && layout.title.length) {
+ return layout.title
+ }
-export default function (layout, metaData) {
if (layout.columns) {
const firstItem = layout.columns[0].items[0]
@@ -10,6 +19,5 @@ export default function (layout, metaData) {
return getFilterText([column], metaData)
}
-
return ''
}
diff --git a/src/visualizations/config/adapters/dhis_highcharts/type.js b/src/visualizations/config/adapters/dhis_highcharts/type.js
index bc56c6d98..08cb62a49 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/type.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/type.js
@@ -12,6 +12,7 @@ import {
VIS_TYPE_STACKED_COLUMN,
VIS_TYPE_YEAR_OVER_YEAR_COLUMN,
VIS_TYPE_SCATTER,
+ VIS_TYPE_SINGLE_VALUE,
} from '../../../../modules/visTypes.js'
export default function (type) {
@@ -33,6 +34,8 @@ export default function (type) {
return { type: 'solidgauge' }
case VIS_TYPE_SCATTER:
return { type: 'scatter', zoomType: 'xy' }
+ case VIS_TYPE_SINGLE_VALUE:
+ return {}
case VIS_TYPE_COLUMN:
case VIS_TYPE_STACKED_COLUMN:
case VIS_TYPE_YEAR_OVER_YEAR_COLUMN:
diff --git a/src/visualizations/config/adapters/dhis_highcharts/xAxis/index.js b/src/visualizations/config/adapters/dhis_highcharts/xAxis/index.js
index c3af4b20b..1439fc201 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/xAxis/index.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/xAxis/index.js
@@ -16,6 +16,7 @@ import {
VIS_TYPE_RADAR,
VIS_TYPE_SCATTER,
isTwoCategoryChartType,
+ VIS_TYPE_SINGLE_VALUE,
} from '../../../../../modules/visTypes.js'
import { getAxis } from '../../../../util/axes.js'
import getAxisTitle from '../getAxisTitle.js'
@@ -82,6 +83,7 @@ export default function (store, layout, extraOptions, series) {
switch (layout.type) {
case VIS_TYPE_PIE:
case VIS_TYPE_GAUGE:
+ case VIS_TYPE_SINGLE_VALUE:
xAxis = noAxis()
break
case VIS_TYPE_YEAR_OVER_YEAR_LINE:
diff --git a/src/visualizations/config/adapters/dhis_highcharts/yAxis/index.js b/src/visualizations/config/adapters/dhis_highcharts/yAxis/index.js
index 1e9aab2a9..d253acdff 100644
--- a/src/visualizations/config/adapters/dhis_highcharts/yAxis/index.js
+++ b/src/visualizations/config/adapters/dhis_highcharts/yAxis/index.js
@@ -11,6 +11,7 @@ import {
isStacked,
VIS_TYPE_GAUGE,
VIS_TYPE_SCATTER,
+ VIS_TYPE_SINGLE_VALUE,
} from '../../../../../modules/visTypes.js'
import { getAxis } from '../../../../util/axes.js'
import { getAxisStringFromId } from '../../../../util/axisId.js'
@@ -148,14 +149,12 @@ function getDefault(layout, series, extraOptions) {
}
export default function (layout, series, extraOptions) {
- let yAxis
switch (layout.type) {
+ case VIS_TYPE_SINGLE_VALUE:
+ return null
case VIS_TYPE_GAUGE:
- yAxis = getGauge(layout, series, extraOptions.legendSets[0])
- break
+ return getGauge(layout, series, extraOptions.legendSets[0])
default:
- yAxis = getDefault(layout, series, extraOptions)
+ return getDefault(layout, series, extraOptions)
}
-
- return yAxis
}
diff --git a/src/visualizations/config/adapters/index.js b/src/visualizations/config/adapters/index.js
index 7b49438ee..4db1838e0 100644
--- a/src/visualizations/config/adapters/index.js
+++ b/src/visualizations/config/adapters/index.js
@@ -1,7 +1,5 @@
-import dhis_dhis from './dhis_dhis/index.js'
import dhis_highcharts from './dhis_highcharts/index.js'
export default {
dhis_highcharts,
- dhis_dhis,
}
diff --git a/src/visualizations/config/generators/dhis/index.js b/src/visualizations/config/generators/dhis/index.js
deleted file mode 100644
index b5a6c3958..000000000
--- a/src/visualizations/config/generators/dhis/index.js
+++ /dev/null
@@ -1,36 +0,0 @@
-import { VIS_TYPE_SINGLE_VALUE } from '../../../../modules/visTypes.js'
-import getSingleValueGenerator from './singleValue.js'
-
-export default function (config, parentEl, extraOptions) {
- if (config) {
- const node =
- typeof parentEl === 'object'
- ? parentEl
- : typeof parentEl === 'string'
- ? document.querySelector(parentEl)
- : null
-
- if (node) {
- if (node.lastChild) {
- node.removeChild(node.lastChild)
- }
-
- let content
-
- switch (config.type) {
- case VIS_TYPE_SINGLE_VALUE:
- default:
- content = getSingleValueGenerator(
- config,
- node,
- extraOptions
- )
- break
- }
-
- node.appendChild(content)
-
- return node.innerHTML
- }
- }
-}
diff --git a/src/visualizations/config/generators/dhis/singleValue.js b/src/visualizations/config/generators/dhis/singleValue.js
deleted file mode 100644
index 25ec5bab9..000000000
--- a/src/visualizations/config/generators/dhis/singleValue.js
+++ /dev/null
@@ -1,531 +0,0 @@
-import { colors } from '@dhis2/ui'
-import {
- FONT_STYLE_VISUALIZATION_TITLE,
- FONT_STYLE_VISUALIZATION_SUBTITLE,
- FONT_STYLE_OPTION_FONT_SIZE,
- FONT_STYLE_OPTION_TEXT_COLOR,
- FONT_STYLE_OPTION_TEXT_ALIGN,
- FONT_STYLE_OPTION_ITALIC,
- FONT_STYLE_OPTION_BOLD,
- TEXT_ALIGN_LEFT,
- TEXT_ALIGN_RIGHT,
- TEXT_ALIGN_CENTER,
- mergeFontStyleWithDefault,
- defaultFontStyle,
-} from '../../../../modules/fontStyle.js'
-import {
- getColorByValueFromLegendSet,
- LEGEND_DISPLAY_STYLE_FILL,
-} from '../../../../modules/legends.js'
-
-const svgNS = 'http://www.w3.org/2000/svg'
-
-// multiply text width with this factor
-// to get very close to actual text width
-// nb: dependent on viewbox etc
-const ACTUAL_TEXT_WIDTH_FACTOR = 0.9
-
-// multiply value text size with this factor
-// to get very close to the actual number height
-// as numbers don't go below the baseline like e.g. "j" and "g"
-const ACTUAL_NUMBER_HEIGHT_FACTOR = 0.67
-
-// do not allow text width to exceed this threshold
-// a threshold >1 does not really make sense but text width vs viewbox is complicated
-const TEXT_WIDTH_CONTAINER_WIDTH_FACTOR = 1.3
-
-// do not allow text size to exceed this
-const TEXT_SIZE_CONTAINER_HEIGHT_FACTOR = 0.6
-const TEXT_SIZE_MAX_THRESHOLD = 400
-
-// multiply text size with this factor
-// to get an appropriate letter spacing
-const LETTER_SPACING_TEXT_SIZE_FACTOR = (1 / 35) * -1
-const LETTER_SPACING_MIN_THRESHOLD = -6
-const LETTER_SPACING_MAX_THRESHOLD = -1
-
-// fixed top margin above title/subtitle
-const TOP_MARGIN_FIXED = 16
-
-// multiply text size with this factor
-// to get an appropriate sub text size
-const SUB_TEXT_SIZE_FACTOR = 0.5
-const SUB_TEXT_SIZE_MIN_THRESHOLD = 26
-const SUB_TEXT_SIZE_MAX_THRESHOLD = 40
-
-// multiply text size with this factor
-// to get an appropriate icon padding
-const ICON_PADDING_FACTOR = 0.3
-
-// Compute text width before rendering
-// Not exactly precise but close enough
-const getTextWidth = (text, font) => {
- const canvas = document.createElement('canvas')
- const context = canvas.getContext('2d')
- context.font = font
- return Math.round(
- context.measureText(text).width * ACTUAL_TEXT_WIDTH_FACTOR
- )
-}
-
-const getTextHeightForNumbers = (textSize) =>
- textSize * ACTUAL_NUMBER_HEIGHT_FACTOR
-
-const getIconPadding = (textSize) => Math.round(textSize * ICON_PADDING_FACTOR)
-
-const getTextSize = (
- formattedValue,
- containerWidth,
- containerHeight,
- showIcon
-) => {
- let size = Math.min(
- Math.round(containerHeight * TEXT_SIZE_CONTAINER_HEIGHT_FACTOR),
- TEXT_SIZE_MAX_THRESHOLD
- )
-
- const widthThreshold = Math.round(
- containerWidth * TEXT_WIDTH_CONTAINER_WIDTH_FACTOR
- )
-
- const textWidth =
- getTextWidth(formattedValue, `${size}px Roboto`) +
- (showIcon ? getIconPadding(size) : 0)
-
- if (textWidth > widthThreshold) {
- size = Math.round(size * (widthThreshold / textWidth))
- }
-
- return size
-}
-
-const generateValueSVG = ({
- formattedValue,
- subText,
- valueColor,
- textColor,
- icon,
- noData,
- containerWidth,
- containerHeight,
- topMargin = 0,
-}) => {
- const showIcon = icon && formattedValue !== noData.text
-
- const textSize = getTextSize(
- formattedValue,
- containerWidth,
- containerHeight,
- showIcon
- )
-
- const textWidth = getTextWidth(formattedValue, `${textSize}px Roboto`)
-
- const iconSize = textSize
-
- const subTextSize =
- textSize * SUB_TEXT_SIZE_FACTOR > SUB_TEXT_SIZE_MAX_THRESHOLD
- ? SUB_TEXT_SIZE_MAX_THRESHOLD
- : textSize * SUB_TEXT_SIZE_FACTOR < SUB_TEXT_SIZE_MIN_THRESHOLD
- ? SUB_TEXT_SIZE_MIN_THRESHOLD
- : textSize * SUB_TEXT_SIZE_FACTOR
-
- const svgValue = document.createElementNS(svgNS, 'svg')
- svgValue.setAttribute('viewBox', `0 0 ${containerWidth} ${containerHeight}`)
- svgValue.setAttribute('width', '50%')
- svgValue.setAttribute('height', '50%')
- svgValue.setAttribute('x', '50%')
- svgValue.setAttribute('y', '50%')
- svgValue.setAttribute('style', 'overflow: visible')
-
- let fillColor = colors.grey900
-
- if (valueColor) {
- fillColor = valueColor
- } else if (formattedValue === noData.text) {
- fillColor = colors.grey600
- }
-
- // show icon if configured in maintenance app
- if (showIcon) {
- // embed icon to allow changing color
- // (elements with fill need to use "currentColor" for this to work)
- const iconSvgNode = document.createElementNS(svgNS, 'svg')
- iconSvgNode.setAttribute('viewBox', '0 0 48 48')
- iconSvgNode.setAttribute('width', iconSize)
- iconSvgNode.setAttribute('height', iconSize)
- iconSvgNode.setAttribute('y', (iconSize / 2 - topMargin / 2) * -1)
- iconSvgNode.setAttribute(
- 'x',
- `-${(iconSize + getIconPadding(textSize) + textWidth) / 2}`
- )
- iconSvgNode.setAttribute('style', `color: ${fillColor}`)
- iconSvgNode.setAttribute('data-test', 'visualization-icon')
-
- const parser = new DOMParser()
- const svgIconDocument = parser.parseFromString(icon, 'image/svg+xml')
-
- Array.from(svgIconDocument.documentElement.children).forEach((node) =>
- iconSvgNode.appendChild(node)
- )
-
- svgValue.appendChild(iconSvgNode)
- }
-
- const letterSpacing = Math.round(textSize * LETTER_SPACING_TEXT_SIZE_FACTOR)
-
- const textNode = document.createElementNS(svgNS, 'text')
- textNode.setAttribute('font-size', textSize)
- textNode.setAttribute('font-weight', '300')
- textNode.setAttribute(
- 'letter-spacing',
- letterSpacing < LETTER_SPACING_MIN_THRESHOLD
- ? LETTER_SPACING_MIN_THRESHOLD
- : letterSpacing > LETTER_SPACING_MAX_THRESHOLD
- ? LETTER_SPACING_MAX_THRESHOLD
- : letterSpacing
- )
- textNode.setAttribute('text-anchor', 'middle')
- textNode.setAttribute(
- 'x',
- showIcon ? `${(iconSize + getIconPadding(textSize)) / 2}` : 0
- )
- textNode.setAttribute(
- 'y',
- topMargin / 2 + getTextHeightForNumbers(textSize) / 2
- )
- textNode.setAttribute('fill', fillColor)
- textNode.setAttribute('data-test', 'visualization-primary-value')
-
- textNode.appendChild(document.createTextNode(formattedValue))
-
- svgValue.appendChild(textNode)
-
- if (subText) {
- const subTextNode = document.createElementNS(svgNS, 'text')
- subTextNode.setAttribute('text-anchor', 'middle')
- subTextNode.setAttribute('font-size', subTextSize)
- subTextNode.setAttribute('y', iconSize / 2 + topMargin / 2)
- subTextNode.setAttribute('dy', subTextSize * 1.7)
- subTextNode.setAttribute('fill', textColor)
- subTextNode.appendChild(document.createTextNode(subText))
-
- svgValue.appendChild(subTextNode)
- }
-
- return svgValue
-}
-
-const generateDashboardItem = (
- config,
- {
- svgContainer,
- width,
- height,
- valueColor,
- titleColor,
- backgroundColor,
- noData,
- icon,
- }
-) => {
- svgContainer.appendChild(
- generateValueSVG({
- formattedValue: config.formattedValue,
- subText: config.subText,
- valueColor,
- textColor: titleColor,
- noData,
- icon,
- containerWidth: width,
- containerHeight: height,
- })
- )
-
- const container = document.createElement('div')
- container.setAttribute(
- 'style',
- `display: flex; flex-direction: column; align-items: center; justify-content: center; width: 100%; height: 100%; padding-top: 8px; ${
- backgroundColor ? `background-color:${backgroundColor};` : ''
- }`
- )
-
- const titleStyle = `padding: 0 8px; text-align: center; font-size: 12px; color: ${
- titleColor || '#666'
- };`
-
- const title = document.createElement('span')
- title.setAttribute('style', titleStyle)
- if (config.title) {
- title.appendChild(document.createTextNode(config.title))
-
- container.appendChild(title)
- }
-
- if (config.subtitle) {
- const subtitle = document.createElement('span')
- subtitle.setAttribute('style', titleStyle + ' margin-top: 4px;')
-
- subtitle.appendChild(document.createTextNode(config.subtitle))
-
- container.appendChild(subtitle)
- }
-
- container.appendChild(svgContainer)
-
- return container
-}
-
-const getTextAnchorFromTextAlign = (textAlign) => {
- switch (textAlign) {
- default:
- case TEXT_ALIGN_LEFT:
- return 'start'
- case TEXT_ALIGN_CENTER:
- return 'middle'
- case TEXT_ALIGN_RIGHT:
- return 'end'
- }
-}
-
-const getXFromTextAlign = (textAlign) => {
- switch (textAlign) {
- default:
- case TEXT_ALIGN_LEFT:
- return '1%'
- case TEXT_ALIGN_CENTER:
- return '50%'
- case TEXT_ALIGN_RIGHT:
- return '99%'
- }
-}
-
-const generateDVItem = (
- config,
- {
- svgContainer,
- width,
- height,
- valueColor,
- noData,
- backgroundColor,
- titleColor,
- fontStyle,
- icon,
- }
-) => {
- if (backgroundColor) {
- svgContainer.setAttribute(
- 'style',
- `background-color: ${backgroundColor};`
- )
-
- const background = document.createElementNS(svgNS, 'rect')
- background.setAttribute('width', '100%')
- background.setAttribute('height', '100%')
- background.setAttribute('fill', backgroundColor)
- svgContainer.appendChild(background)
- }
-
- const svgWrapper = document.createElementNS(svgNS, 'svg')
-
- // title
- const title = document.createElementNS(svgNS, 'text')
-
- const titleFontStyle = mergeFontStyleWithDefault(
- fontStyle && fontStyle[FONT_STYLE_VISUALIZATION_TITLE],
- FONT_STYLE_VISUALIZATION_TITLE
- )
-
- const titleYPosition =
- TOP_MARGIN_FIXED +
- parseInt(titleFontStyle[FONT_STYLE_OPTION_FONT_SIZE]) +
- 'px'
-
- const titleAttributes = {
- x: getXFromTextAlign(titleFontStyle[FONT_STYLE_OPTION_TEXT_ALIGN]),
- y: titleYPosition,
- 'text-anchor': getTextAnchorFromTextAlign(
- titleFontStyle[FONT_STYLE_OPTION_TEXT_ALIGN]
- ),
- 'font-size': `${titleFontStyle[FONT_STYLE_OPTION_FONT_SIZE]}px`,
- 'font-weight': titleFontStyle[FONT_STYLE_OPTION_BOLD]
- ? FONT_STYLE_OPTION_BOLD
- : 'normal',
- 'font-style': titleFontStyle[FONT_STYLE_OPTION_ITALIC]
- ? FONT_STYLE_OPTION_ITALIC
- : 'normal',
- 'data-test': 'visualization-title',
- fill:
- titleColor &&
- titleFontStyle[FONT_STYLE_OPTION_TEXT_COLOR] ===
- defaultFontStyle[FONT_STYLE_VISUALIZATION_TITLE][
- FONT_STYLE_OPTION_TEXT_COLOR
- ]
- ? titleColor
- : titleFontStyle[FONT_STYLE_OPTION_TEXT_COLOR],
- }
-
- Object.entries(titleAttributes).forEach(([key, value]) =>
- title.setAttribute(key, value)
- )
-
- if (config.title) {
- title.appendChild(document.createTextNode(config.title))
- svgWrapper.appendChild(title)
- }
-
- // subtitle
- const subtitle = document.createElementNS(svgNS, 'text')
-
- const subtitleFontStyle = mergeFontStyleWithDefault(
- fontStyle && fontStyle[FONT_STYLE_VISUALIZATION_SUBTITLE],
- FONT_STYLE_VISUALIZATION_SUBTITLE
- )
-
- const subtitleAttributes = {
- x: getXFromTextAlign(subtitleFontStyle[FONT_STYLE_OPTION_TEXT_ALIGN]),
- y: titleYPosition,
- dy: `${subtitleFontStyle[FONT_STYLE_OPTION_FONT_SIZE] + 10}`,
- 'text-anchor': getTextAnchorFromTextAlign(
- subtitleFontStyle[FONT_STYLE_OPTION_TEXT_ALIGN]
- ),
- 'font-size': `${subtitleFontStyle[FONT_STYLE_OPTION_FONT_SIZE]}px`,
- 'font-weight': subtitleFontStyle[FONT_STYLE_OPTION_BOLD]
- ? FONT_STYLE_OPTION_BOLD
- : 'normal',
- 'font-style': subtitleFontStyle[FONT_STYLE_OPTION_ITALIC]
- ? FONT_STYLE_OPTION_ITALIC
- : 'normal',
- fill:
- titleColor &&
- subtitleFontStyle[FONT_STYLE_OPTION_TEXT_COLOR] ===
- defaultFontStyle[FONT_STYLE_VISUALIZATION_SUBTITLE][
- FONT_STYLE_OPTION_TEXT_COLOR
- ]
- ? titleColor
- : subtitleFontStyle[FONT_STYLE_OPTION_TEXT_COLOR],
- 'data-test': 'visualization-subtitle',
- }
-
- Object.entries(subtitleAttributes).forEach(([key, value]) =>
- subtitle.setAttribute(key, value)
- )
-
- if (config.subtitle) {
- subtitle.appendChild(document.createTextNode(config.subtitle))
- svgWrapper.appendChild(subtitle)
- }
-
- svgContainer.appendChild(svgWrapper)
-
- svgContainer.appendChild(
- generateValueSVG({
- formattedValue: config.formattedValue,
- subText: config.subText,
- valueColor,
- textColor: titleColor,
- noData,
- icon,
- containerWidth: width,
- containerHeight: height,
- topMargin:
- TOP_MARGIN_FIXED +
- ((config.title
- ? parseInt(title.getAttribute('font-size'))
- : 0) +
- (config.subtitle
- ? parseInt(subtitle.getAttribute('font-size'))
- : 0)) *
- 2.5,
- })
- )
-
- return svgContainer
-}
-
-const shouldUseContrastColor = (inputColor = '') => {
- // based on https://stackoverflow.com/questions/3942878/how-to-decide-font-color-in-white-or-black-depending-on-background-color
- var color =
- inputColor.charAt(0) === '#' ? inputColor.substring(1, 7) : inputColor
- var r = parseInt(color.substring(0, 2), 16) // hexToR
- var g = parseInt(color.substring(2, 4), 16) // hexToG
- var b = parseInt(color.substring(4, 6), 16) // hexToB
- var uicolors = [r / 255, g / 255, b / 255]
- var c = uicolors.map((col) => {
- if (col <= 0.03928) {
- return col / 12.92
- }
- return Math.pow((col + 0.055) / 1.055, 2.4)
- })
- var L = 0.2126 * c[0] + 0.7152 * c[1] + 0.0722 * c[2]
- return L <= 0.179
-}
-
-export default function (
- config,
- parentEl,
- { dashboard, legendSets, fontStyle, noData, legendOptions, icon }
-) {
- const legendSet = legendOptions && legendSets[0]
- const legendColor =
- legendSet && getColorByValueFromLegendSet(legendSet, config.value)
- let valueColor, titleColor, backgroundColor
- if (legendColor) {
- if (legendOptions.style === LEGEND_DISPLAY_STYLE_FILL) {
- backgroundColor = legendColor
- valueColor = titleColor =
- shouldUseContrastColor(legendColor) && colors.white
- } else {
- valueColor = legendColor
- }
- }
-
- parentEl.style.overflow = 'hidden'
- parentEl.style.display = 'flex'
- parentEl.style.justifyContent = 'center'
-
- const parentElBBox = parentEl.getBoundingClientRect()
- const width = parentElBBox.width
- const height = parentElBBox.height
-
- const svgContainer = document.createElementNS(svgNS, 'svg')
- svgContainer.setAttribute('xmlns', svgNS)
- svgContainer.setAttribute('viewBox', `0 0 ${width} ${height}`)
- svgContainer.setAttribute('width', dashboard ? '100%' : width)
- svgContainer.setAttribute('height', dashboard ? '100%' : height)
- svgContainer.setAttribute('data-test', 'visualization-container')
-
- if (dashboard) {
- parentEl.style.borderRadius = '3px'
-
- return generateDashboardItem(config, {
- svgContainer,
- width,
- height,
- valueColor,
- backgroundColor,
- noData,
- icon,
- ...(legendOptions.style === LEGEND_DISPLAY_STYLE_FILL &&
- legendColor &&
- shouldUseContrastColor(legendColor)
- ? { titleColor: colors.white }
- : {}),
- })
- } else {
- parentEl.style.height = `100%`
-
- return generateDVItem(config, {
- svgContainer,
- width,
- height,
- valueColor,
- backgroundColor,
- titleColor,
- noData,
- icon,
- fontStyle,
- })
- }
-}
diff --git a/src/visualizations/config/generators/highcharts/index.js b/src/visualizations/config/generators/highcharts/index.js
index 92a775910..3620e81f5 100644
--- a/src/visualizations/config/generators/highcharts/index.js
+++ b/src/visualizations/config/generators/highcharts/index.js
@@ -3,16 +3,24 @@ import HM from 'highcharts/highcharts-more'
import HB from 'highcharts/modules/boost'
import HE from 'highcharts/modules/exporting'
import HNDTD from 'highcharts/modules/no-data-to-display'
+import HOE from 'highcharts/modules/offline-exporting'
import HPF from 'highcharts/modules/pattern-fill'
import HSG from 'highcharts/modules/solid-gauge'
+import PEBFP from './pdfExportBugFixPlugin/index.js'
// apply
HM(H)
HSG(H)
HNDTD(H)
HE(H)
+HOE(H)
HPF(H)
HB(H)
+PEBFP(H)
+
+/* Whitelist some additional SVG attributes here. Without this,
+ * the PDF export for the SingleValue visualization breaks. */
+H.AST.allowedAttributes.push('fill-rule', 'clip-rule')
function drawLegendSymbolWrap() {
const pick = H.pick
@@ -75,7 +83,6 @@ export default function (config, el) {
// silence warning about accessibility
config.accessibility = { enabled: false }
-
if (config.lang) {
H.setOptions({
lang: config.lang,
diff --git a/src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/index.js b/src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/index.js
new file mode 100644
index 000000000..7b4899cde
--- /dev/null
+++ b/src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/index.js
@@ -0,0 +1,7 @@
+import nonASCIIFontBugfix from './nonASCIIFont.js'
+import textShadowBugFix from './textShadow.js'
+
+export default function (H) {
+ textShadowBugFix(H)
+ nonASCIIFontBugfix(H)
+}
diff --git a/src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/nonASCIIFont.js b/src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/nonASCIIFont.js
new file mode 100644
index 000000000..d2c8d9835
--- /dev/null
+++ b/src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/nonASCIIFont.js
@@ -0,0 +1,9 @@
+/* This is a workaround for https://github.com/highcharts/highcharts/issues/22008
+ * We add some transparent text in a non-ASCII script to the chart to prevent
+ * the chart from being exported in a serif font */
+
+export default function (H) {
+ H.addEvent(H.Chart, 'load', function () {
+ this.renderer.text('모', 20, 20).attr({ opacity: 0 }).add()
+ })
+}
diff --git a/src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/textShadow.js b/src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/textShadow.js
new file mode 100644
index 000000000..21a96e1a5
--- /dev/null
+++ b/src/visualizations/config/generators/highcharts/pdfExportBugFixPlugin/textShadow.js
@@ -0,0 +1,308 @@
+/* This plugin was provided by HighCharts support and resolves an issue with label
+ * text that has a white outline, such as the one we use for stacked bar charts.
+ * For example: "ANC: 1-4 visits by districts this year (stacked)"
+ * This issue has actually been resolved in HighCharts v11, so once we have upgraded
+ * to that version, this plugin can be removed. */
+
+export default function (H) {
+ const { AST, defaultOptions, downloadURL } = H,
+ { ajax } = H.HttpUtilities,
+ doc = document,
+ win = window,
+ OfflineExporting =
+ H._modules['Extensions/OfflineExporting/OfflineExporting.js'],
+ { getScript, svgToPdf, imageToDataUrl, svgToDataUrl } = OfflineExporting
+
+ H.wrap(
+ OfflineExporting,
+ 'downloadSVGLocal',
+ function (proceed, svg, options, failCallback, successCallback) {
+ var dummySVGContainer = doc.createElement('div'),
+ imageType = options.type || 'image/png',
+ filename =
+ (options.filename || 'chart') +
+ '.' +
+ (imageType === 'image/svg+xml'
+ ? 'svg'
+ : imageType.split('/')[1]),
+ scale = options.scale || 1
+ var svgurl,
+ blob,
+ finallyHandler,
+ libURL = options.libURL || defaultOptions.exporting.libURL,
+ objectURLRevoke = true,
+ pdfFont = options.pdfFont
+ // Allow libURL to end with or without fordward slash
+ libURL = libURL.slice(-1) !== '/' ? libURL + '/' : libURL
+ /*
+ * Detect if we need to load TTF fonts for the PDF, then load them and
+ * proceed.
+ *
+ * @private
+ */
+ var loadPdfFonts = function (svgElement, callback) {
+ var hasNonASCII = function (s) {
+ return (
+ // eslint-disable-next-line no-control-regex
+ /[^\u0000-\u007F\u200B]+/.test(s)
+ )
+ }
+ // Register an event in order to add the font once jsPDF is
+ // initialized
+ var addFont = function (variant, base64) {
+ win.jspdf.jsPDF.API.events.push([
+ 'initialized',
+ function () {
+ this.addFileToVFS(variant, base64)
+ this.addFont(variant, 'HighchartsFont', variant)
+ if (!this.getFontList().HighchartsFont) {
+ this.setFont('HighchartsFont')
+ }
+ },
+ ])
+ }
+ // If there are no non-ASCII characters in the SVG, do not use
+ // bother downloading the font files
+ if (pdfFont && !hasNonASCII(svgElement.textContent || '')) {
+ pdfFont = void 0
+ }
+ // Add new font if the URL is declared, #6417.
+ var variants = ['normal', 'italic', 'bold', 'bolditalic']
+ // Shift the first element off the variants and add as a font.
+ // Then asynchronously trigger the next variant until calling the
+ // callback when the variants are empty.
+ var normalBase64
+ var shiftAndLoadVariant = function () {
+ var variant = variants.shift()
+ // All variants shifted and possibly loaded, proceed
+ if (!variant) {
+ return callback()
+ }
+ var url = pdfFont && pdfFont[variant]
+ if (url) {
+ ajax({
+ url: url,
+ responseType: 'blob',
+ success: function (data, xhr) {
+ var reader = new FileReader()
+ reader.onloadend = function () {
+ if (typeof this.result === 'string') {
+ var base64 = this.result.split(',')[1]
+ addFont(variant, base64)
+ if (variant === 'normal') {
+ normalBase64 = base64
+ }
+ }
+ shiftAndLoadVariant()
+ }
+ reader.readAsDataURL(xhr.response)
+ },
+ error: shiftAndLoadVariant,
+ })
+ } else {
+ // For other variants, fall back to normal text weight/style
+ if (normalBase64) {
+ addFont(variant, normalBase64)
+ }
+ shiftAndLoadVariant()
+ }
+ }
+ shiftAndLoadVariant()
+ }
+ /*
+ * @private
+ */
+ var downloadPDF = function () {
+ AST.setElementHTML(dummySVGContainer, svg)
+ var textElements =
+ dummySVGContainer.getElementsByTagName('text'),
+ // Copy style property to element from parents if it's not
+ // there. Searches up hierarchy until it finds prop, or hits the
+ // chart container.
+ setStylePropertyFromParents = function (el, propName) {
+ var curParent = el
+ while (curParent && curParent !== dummySVGContainer) {
+ if (curParent.style[propName]) {
+ el.style[propName] = curParent.style[propName]
+ break
+ }
+ curParent = curParent.parentNode
+ }
+ }
+ var titleElements,
+ outlineElements
+ // Workaround for the text styling. Making sure it does pick up
+ // settings for parent elements.
+ ;[].forEach.call(textElements, function (el) {
+ // Workaround for the text styling. making sure it does pick up
+ // the root element
+ ;['font-family', 'font-size'].forEach(function (property) {
+ setStylePropertyFromParents(el, property)
+ })
+ el.style.fontFamily =
+ pdfFont && pdfFont.normal
+ ? // Custom PDF font
+ 'HighchartsFont'
+ : // Generic font (serif, sans-serif etc)
+ String(
+ el.style.fontFamily &&
+ el.style.fontFamily.split(' ').splice(-1)
+ )
+ // Workaround for plotband with width, removing title from text
+ // nodes
+ titleElements = el.getElementsByTagName('title')
+ ;[].forEach.call(titleElements, function (titleElement) {
+ el.removeChild(titleElement)
+ })
+
+ // Remove all .highcharts-text-outline elements, #17170
+ outlineElements = el.getElementsByClassName(
+ 'highcharts-text-outline'
+ )
+ while (outlineElements.length > 0) {
+ const outline = outlineElements[0]
+ if (outline.parentNode) {
+ outline.parentNode.removeChild(outline)
+ }
+ }
+ })
+ var svgNode = dummySVGContainer.querySelector('svg')
+ if (svgNode) {
+ loadPdfFonts(svgNode, function () {
+ svgToPdf(svgNode, 0, function (pdfData) {
+ try {
+ downloadURL(pdfData, filename)
+ if (successCallback) {
+ successCallback()
+ }
+ } catch (e) {
+ failCallback(e)
+ }
+ })
+ })
+ }
+ }
+ // Initiate download depending on file type
+ if (imageType === 'image/svg+xml') {
+ // SVG download. In this case, we want to use Microsoft specific
+ // Blob if available
+ try {
+ if (typeof win.navigator.msSaveOrOpenBlob !== 'undefined') {
+ // eslint-disable-next-line no-undef
+ blob = new MSBlobBuilder()
+ blob.append(svg)
+ svgurl = blob.getBlob('image/svg+xml')
+ } else {
+ svgurl = svgToDataUrl(svg)
+ }
+ downloadURL(svgurl, filename)
+ if (successCallback) {
+ successCallback()
+ }
+ } catch (e) {
+ failCallback(e)
+ }
+ } else if (imageType === 'application/pdf') {
+ if (win.jspdf && win.jspdf.jsPDF) {
+ downloadPDF()
+ } else {
+ // Must load pdf libraries first. // Don't destroy the object
+ // URL yet since we are doing things asynchronously. A cleaner
+ // solution would be nice, but this will do for now.
+ objectURLRevoke = true
+ getScript(libURL + 'jspdf.js', function () {
+ getScript(libURL + 'svg2pdf.js', downloadPDF)
+ })
+ }
+ } else {
+ // PNG/JPEG download - create bitmap from SVG
+ svgurl = svgToDataUrl(svg)
+ finallyHandler = function () {
+ try {
+ OfflineExporting.domurl.revokeObjectURL(svgurl)
+ } catch (e) {
+ // Ignore
+ }
+ }
+ // First, try to get PNG by rendering on canvas
+ imageToDataUrl(
+ svgurl,
+ imageType,
+ {},
+ scale,
+ function (imageURL) {
+ // Success
+ try {
+ downloadURL(imageURL, filename)
+ if (successCallback) {
+ successCallback()
+ }
+ } catch (e) {
+ failCallback(e)
+ }
+ },
+ function () {
+ // Failed due to tainted canvas
+ // Create new and untainted canvas
+ var canvas = doc.createElement('canvas'),
+ ctx = canvas.getContext('2d'),
+ imageWidth =
+ svg.match(
+ // eslint-disable-next-line no-useless-escape
+ /^